Skip to main content

Требования к заморозке

Общие принципы «заморозки»

  1. Что такое заморозка?
    Заморозка — это резервирование части ресурса (баллов, сертификата или одноразового промокода) на выбранный период, в течение которого этот ресурс считается недоступным для любых других операций.

  2. Срок действия

    • При создании можно передать либо абсолютную дату окончания, либо относительный интервал (например, «через 7 дней»).

    • Если срок не указан, применяются настройки организации (по умолчанию — 14 дней). 

    • По достижении даты окончания заморозка автоматически истекает.

  3. Состояния заморозки

    • ACTIVE — ресурс заблокирован, используется в продаже или ожидает использования.

    • USED — ресурс был применён в документе продажи.

    • EXPIRED — заморозка истекла, невостребованное возвращается пользователю (если ещё не истекло).

    • CANCELLED — заморозка снята досрочно, невостребованное возвращается пользователю (если ещё не истекло).

  4. Взаимодействие с продажей

    • При оформлении чека мы можем передать одну или несколько заморозок сертификатов или баллов (промокоды только один).

    • Если в чеке передана заморозка баллов, при расчёте скидки сначала списываются из неё, а остаток (если нужно) по стандартной схеме.

    • Возможно частичное использование заморозок баллов и сертификатов: передаётся, какую именно сумму/количество баллов из заморозки потратить.

    • Флаг "hold_used" (или аналог) определяет: удалять ли остаток заморозки (и возвращать этот остаток в доступный баланс) или оставить её дальше активной с уменьшённым количеством сумма/количеством баллов.

  5. Автоматическое истечение
    Любая активная-заморозка по достижению времени сгорания переводится в истёкшую автоматически. В этом случае поведение как при статусе CANCELLED, невостребованное возвращается пользователю (если ещё не истекло, если истекло, то сгорает).


1. Заморозка баллов

  1. Создание

    • Бизнес-правило: клиент просит «заблокировать» N баллов.

    • Условия: у клиента должно быть ≥ N свободных (не замороженных и не сгоревших) баллов.

    • Результат: N баллов переходит в состояние «заморожено» (ACTIVE), и исчезает из обычного баланса.

  2. Использование в продаже

    • При расчёте скидки сначала берутся баллы из заморозки.

    • Можно указать, сколько из замороженных баллов списать в этой операции; по умолчанию — всё.

    • Если продажа требует больше баллов, остаток добирается из обычного (ненарезервированного) балльного баланса.

    • После списания:

      • hold_used= true (по умолчанию) → заморозка удаляется; всё неиспользованное (и ещё не истекшее) возвращается в обычный баланс (или сгорают если должны были сгореть по условиям сгорания).

      • hold_used = false → заморозка остаётся, но её объём уменьшается на списанную часть.

  3. Отмена заморозки

    • Клиент или система может отозвать заморозку до её использования.

    • Если дата отмены < expires_at — остаток возвращается в баланс, или сгорает/истекает если должны были по условиям


2. Заморозка одноразового промокода

  1. Объект заморозки
    Применим только к промокодам с типом одноразовый.

    • Если у промокода есть «персональная одноразовасть» привязка к карте или пользователю, мы резервируем только для этой карты — остальные клиенты пока могут использовать (или замораживать) свой собственный промокод.

  2. Создание

    • Проверяем, что промокод ещё не был применён и не заморожен для данного пользователя.

    • Резервируем его на указанный срок (или на дефолтные 14 дней).

  3. Использование в продаже

    • При передаче hold_id в чеке игнорируется любая другая попытка применить «обычный» (незамороженный) промокод.

    • Замороженный промокод переводится в USED и становится недоступным для всех (или, в случае персональной одноразовости, для этой карты).

  4. Отмена/сгорание

    • Если до конца срока промокод не был использован и мы явно отменяем заморозку — промокод снова становится доступным (если дата отмены < expires_at).

    • По истечении срока заморозки заморозка переходит в EXPIRED.


3. Заморозка сертификатов

  1. Создание

    • Опционально можно указать сумму (≤ номинала) для блокировки; иначе блокируется весь номинал.

  2. Использование в продаже

    • В чеке может быть передан массив заморозок по разным сертификатам.

    • Из каждого резервируемого сертификата списывают указанную сумму.

    • Флаг hold_used работает так же, как для баллов:

      • hold_used= true (по умолчанию) → заморозка удаляется; всё неиспользованное (и ещё не истекшее) возвращается в обычный баланс (или истекает если должны были истечь по условиям).

      • hold_used = false → заморозка остаётся, но её объём уменьшается на списанную часть.

  3. Отмена/истечение

    • До истечения срока можно отменить заморозку и вернуть неиспользованное.


Пример сценария «частичная продажа»

  1. Клиент замораживает 1 000 баллов на 10 дней.

  2. Через 3 дня при оплате онлайн формируется скидка в 700 баллов и передаётся hold_id с флагом hold_used= true.

  3. Система списывает 700 из заморозки → в заморозке остаётся 300 баллов. Активная заморозка теперь на 300.

  4. При оформлении ещё одной покупки в течение срока эти 300 могут быть списаны автоматически до своей суммы, затем снова — из обычного баланса или новых заморозок.


Ключевые моменты для реализации

  • Атомарность операций: создание/применение/отмена заморозки должны быть транзакционными.

  • Валидация лимитов: нельзя заблокировать больше, чем есть в доступном балансе; нельзя списать из заморозки больше, чем в ней заблокировано; нельзя использовать просроченный или уже потреблённый ресурс.