Направление работ: Back

Код раздела: 2.4 Объекты и предложения > Правила работы с заказами

Статус: черновик

Ответственный: Панкова Л.А.

Версия: 0.1

Обновлено: 10.07.26


1. Назначение

Раздел описывает параметры, определяющие условия и формат работы с бронированиями в процессинговых статусах для каждой конкретной партнерской зоны.

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

2. Ключевые понятия

Правила работы с заказами — перечень параметров, определяющих условия и формат работы с бронированиями в процессинговых статусах для каждой конкретной партнерской зоны.

Наследование правил — применение правил вышестоящего уровня, пока они не уточнены для нижестоящей сущности.

3. Scope

Входит

S1 Параметры работы с заказами: условия создания, условия оплаты и правила отмены.

S2 Общие процессы: наследование и уточнение правил по уровням предложения.

Не входит

4. Требования

Правила и ограничения бизнеса на уровне данных, источник истины в системе.

IDТребованиеКомментарийТип требованияВесСтатус
S1: BR2.4-1Для каждой конкретной партнерской зоны должен задаваться перечень параметров, определяющих условия и формат работы с бронированиями в процессинговых статусахПараметры раскрываются в разделах Back 2.4.1 Условия создания, Back 2.4.2 Условия оплаты и Back 2.4.3 Правила отменыБизнес1Частично — OQ2.4-6, OQ2.4-7, OQ2.4-8
S2: BR2.4-2Для всех правил работы с заказами должна действовать система наследования, при которой общие сервисные правила уточняются для каждого уровня за счет привязки к соответствующим сущностямСтандартные правила задаются в Back 8.4 Параметры системы, наследуются по умолчанию в настройки каждой новой партнерской зоны и могут уточняться ее владельцем или сотрудником. Партнерская зона раскрывается в Back 1.4 Партнеры.

Уровни наследования:
Сервисная зона - действуют на всю систему пока не уточняются уровнем ниже
Партнерская зона - действуют на всю партнерскую зону пока не уточняются уровнем ниже
Объект в партнерской зоне - действуют на конкретном объекте пока не уточняются уровнем ниже
Площадка или услуга объекта в партнерской зоне - действуют только на отдельном предложении(площадке или услуге)
Бизнес1Частично — OQ2.4-1, OQ2.4-2, OQ2.4-3, OQ2.4-4, OQ2.4-5, OQ2.4-9, OQ2.4-10, OQ2.4-18

5. Открытые вопросы

BRD 2.4 v0.1 · booking-monorepo · commit 83423b21 / main · 2026-07-20 · якорь src/services/booking.partner-management (PartnerZones.Domain/BookingRulesAggregate, PartnerZones.Persistence/BookingRules, PartnerZones.Application/Commands/RuleSet, PartnerZones.Application/Queries/Room/BookingAllowed), а также PartnerZones.Persistence/CancelRules, PartnerZones.Persistence/PaymentFilters и потребитель src/services/booking.orders Сводка: вопросов 18 (Open 13 · Закрывает PM 4 · Подтверждено 1) · отрезано находок обратного прохода 10 Маршрутизация без сверки с гайдбуком (гайдбук на вход не передавался — позиция гайдбука нигде не додумывалась). Охват: сверялась только общая механика зонтичного раздела — состав набора правил, привязка к сущностям и наследование. Содержательные параметры условий создания, оплаты и отмены детально не сверялись, они идут отдельными прогонами по 2.4.1–2.4.3. Оговорка: сервис booking.partner-management не содержит каталога миграций и SQL-файлов — схема создаётся кодом при старте (DbInitializer). Поэтому ограничения и индексы в базе по коду проверить нельзя: все утверждения о базе опираются только на атрибуты маппинга. Отрезано (перечислено, чтобы не читалось как «всё покрыто»): мёртвый параметр options в методе изменения набора правил; восстановление из архива не публикует событие, в отличие от архивации; архивация не использует переданный идентификатор сотрудника; версия события архивации зашита константой; строкам привязки при каждом сохранении присваивается новый идентификатор; проверка «нельзя привязать правила день в день при выключенном бронировании день в день» выполняется только при изменении набора, но не при создании; в массовом изменении наборов список «затронутых» привязок собирается по всему пакету, а не по текущему набору; значение BookingRuleInfo объявлено, но не используется; текстовые правила бронирования (TextBookingRule) — отдельная сущность, в требованиях 2.4 не упомянута и относится к другому разделу; полная очистка правил площадки при смене её часов уже заведена как OQ2.2-8 в сверке Back 2.2 и здесь не дублируется.

IDИсточникВопросКомуСтатусРекомендацииИтоговое решение
OQ2.4-1Код BR2.4-2Требование говорит: наследование работает по четырём уровням — сервисная зона, партнёрская зона, объект, площадка или услуга; каждый следующий уровень уточняет предыдущий. В коде при подборе правил для брони участвуют только два уровня: сначала ищется набор, привязанный к площадке, если его нет — набор, привязанный к объекту. Партнёрская зона в условие подбора вообще не входит, эталон сервисной зоны в подборе не участвует, а «услуги» как сущности в бэкенде нет. То есть из четырёх заявленных уровней реально работают два. — нужно решение: сколько уровней система обязана поддерживать. \ BookingRuleSetRepository.cs:234-235 (отбор кандидатов только по площадке и объекту), :240-245 (приоритет площадка → объект)Бизнес/РазработкаOpenРазблокирующий вопрос: от ответа зависят OQ2.4-3, OQ2.4-4, OQ2.4-5. (А, рекоменд.) зафиксировать в BRD фактическую модель «объект → площадка» и отдельно описать, чем на самом деле является эталон сервисной зоны (см. OQ2.4-3) — код уже работает так, это самая дешёвая правда. (Б) признать четырёхуровневую модель целевой и заводить доработку: подбор должен подниматься до партнёрской зоны и до сервисного эталона.Необходимо подтверждение со стороны бизнеса: принимаем ли фактическую модель наследования только по двум рабочим уровням «объект → площадка» вместо заявленных четырёх уровней. Если бизнес подтверждает 2 уровня, зафиксировать это в BRD как целевое поведение. Если требуется сохранить 4 уровня, это дорогая доработка разработки: нужно менять подбор правил с учётом партнёрской зоны, сервисная зона и сущности «услуга», а также пересматривать связанные вопросы OQ2.4-3, OQ2.4-4, OQ2.4-5.
OQ2.4-2Код BR2.4-2Требование говорит: правила вышестоящего уровня действуют, пока не уточнены уровнем ниже — то есть ожидается уточнение по отдельным параметрам. В коде уточнения по параметрам нет: подбор выбирает ровно один набор правил целиком и на нём останавливается. Если у площадки есть собственный набор, правила объекта не применяются вообще — даже те параметры, которые на площадке не заданы. Партнёр, задавший на площадке одно правило, молча теряет все остальные правила объекта. — нужно решение: наследование по параметрам или замена набора целиком. \ BookingRuleSetRepository.cs:245 (выбирается один набор), :240-244Бизнес (Герман)Open(А, рекоменд.) переписать формулировку BR2.4-2 под фактическую модель «замещение набора целиком», если она устраивает бизнес — иначе требование обещает партнёру поведение, которого нет. (Б) реализовать уточнение по параметрам (собирать итоговый набор из уровней) — существенная доработка, затрагивает все три семейства правил. Связать с OQ2.4-1.Нужно подтвердить с бизнесом: если для площадки задан свой набор правил, он должен полностью заменить правила объекта или только переопределить указанные параметры, а остальные параметры должны наследоваться от объекта. Сейчас код работает как полная замена набора; если бизнес ожидает наследование отдельных параметров, нужна отдельная доработка.
OQ2.4-3Код BR2.4-2Требование говорит: стандартные сервисные правила действуют на всю систему, пока не уточнены уровнем ниже, и наследуются в настройки каждой новой партнерской зоны. В коде это не наследование, а разовое копирование: у эталонного набора сферы намеренно нет ни одной привязки, поэтому в подборе он не участвует никогда. При создании объекта (а также при изменении его часов) система один раз копирует эталон в самостоятельный набор, привязанный к объекту. Дальше связь только справочная: если эталон потом изменить, уже созданные копии не изменятся — механизма до-рассылки нет. Копия всегда создаётся на уровне объекта, на уровень партнёрской зоны — никогда. Отдельный признак незавершённости: сама команда создания сервисного эталона помечена в коде как неиспользуемая ([Obsolete("unused")]). \ CreateSphereRuleSetCommandHandler.cs:65-79 (эталон без привязок), CreateSphereRuleSetCommand.cs:14-15 (пометка «не используется»), CreateFromDefaultCommandHandler.cs:51,68-73 (разовое копирование), BookingRuleSetAggregate.cs:141-172, BaseCreatedPartnerZoneConsumer.cs:73Бизнес (Герман)Open(А, рекоменд.) зафиксировать в BRD, что сервисный уровень — это шаблон при создании объекта, а не действующий уровень наследования, и отдельно описать ожидаемое поведение при изменении эталона (обычно «старые не трогаем») — дёшево и совпадает с кодом. (Б) если бизнес ждёт живого наследования (поправили эталон — поменялось везде, где не уточнено), это отдельная доработка с миграцией уже созданных копий. Попутно нужно решить судьбу помеченной как неиспользуемая команды создания эталона. Связать с OQ2.4-1.Нужно подтвердить с бизнесом назначение сервисных правил. Сейчас код работает так: сервисные правила — это шаблон, который один раз копируется при создании объекта, а не живой уровень наследования. Если бизнес подтверждает это поведение, зафиксировать его в BRD. Если бизнес ожидает, что изменение сервисных правил будет автоматически влиять на существующие объекты, нужна отдельная дорогая доработка живого наследования и миграция уже созданных копий.
OQ2.4-4Код BR2.4-2Требование говорит: правила уровня партнёрской зоны действуют на всю партнёрскую зону, пока не уточнены ниже. В коде уровень партнёрской зоны заведён в хранении (в строке привязки есть обязательное поле партнёрской зоны и необязательные объект и площадка, а комментарий в модели прямо говорит «оба пустых — значит вся партнёрская зона»), но подбор такие строки никогда не выбирает: оба условия отбора требуют заполненного объекта или площадки. Более того, при создании набора выбор одной только партнёрской зоны не создаёт ни одной строки привязки. Итог: данные уровня партнёрской зоны, если их завести, не действуют ни на что. \ BookingRuleSetScope.cs:8-17 (модель привязки), PartnerZoneEntityScope.cs:12-32 (заявленная семантика), BookingRuleSetRepository.cs:234-235 (подбор игнорирует такие строки), CreateRuleSetCommandHandler.cs:66-73Бизнес/РазработкаOpen(А, рекоменд.) если по OQ2.4-1 уровень партнёрской зоны признан нужным — добавить его в подбор третьим приоритетом и разрешить создание привязки к зоне без объектов. (Б) если уровень не нужен — убрать вводящий в заблуждение комментарий о семантике и закрыть возможность создавать такие строки, чтобы в базе не копились данные, которые ни на что не влияют.Зависит от решения по OQ2.4-1. Необходимо подтверждение бизнеса, нужен ли рабочий уровень правил партнёрской зоны. Если бизнес подтверждает двухуровневую модель «объект → площадка», уровень партнёрской зоны нужно убрать из описания целевого поведения и закрыть/очистить неиспользуемую семантику в коде, чтобы не создавать неработающие привязки. Если уровень партнёрской зоны нужен, это отдельная доработка: добавить создание привязки к зоне без объекта/площадки и включить партнёрскую зону в алгоритм подбора правил.
OQ2.4-5Код BR2.4-2Требование говорит: нижний уровень наследования — «площадка или услуга объекта». В коде услуг нет: привязать набор правил можно только к объекту или к площадке, третьего варианта в модели привязки не существует. Поиск сущности «услуга» по всему сервису управления партнёрскими зонами результатов не дал (единственное совпадение по названию — тариф на услуги размещения, к правилам заказов отношения не имеет). — нужно подтверждение: услуга это отдельная сущность или это та же площадка, названная иначе. \ BookingRuleSetScope.cs:8-17, PartnerZoneEntityScope.cs (только партнёрская зона, объект, площадка); поиск по «услуг»/ServiceId в booking.partner-management — совпадений нетБизнес (Герман)Open(А, рекоменд.) если «услуга» — это то же, что площадка (разный способ продажи одного предложения), убрать из BRD противопоставление «площадка или услуга» либо пояснить, что в данных это одна сущность — иначе требование выглядит как нереализованный уровень. (Б) если услуга задумана как отдельная сущность со своими правилами — это крупная доработка модели данных, её нужно ставить в план отдельно. Связать с OQ2.4-1.Нужно подтвердить с бизнесом, что означает «услуга объекта» в этом разделе. Если услуга — это та же площадка/предложение в текущей модели данных, поправить BRD и не выделять её как отдельный уровень правил. Если услуга должна быть отдельной сущностью со своими правилами, это отдельная крупная доработка модели привязок, подбора правил и интерфейсов.
OQ2.4-6Код BR2.4-1Требование говорит: для партнёрской зоны задаётся единый перечень параметров, определяющих условия и формат работы с бронированиями, и все они подчиняются одним правилам наследования. В коде единого перечня нет — это три независимые сущности, каждая со своей таблицей привязок и, что важнее, со своим алгоритмом подбора: условия создания — площадка → объект, без запасного варианта; правила отмены — площадка → объект, а при отсутствии обоих откат к эталону сферы; условия оплаты — не «один победитель», а отбор всех подходящих условий, причём уровень партнёрской зоны там частично работает, но только для одного узкого случая (оплата на месте в вебе). Сервис заказов читает их тремя разными способами: допустимость времени — через проверку правил бронирования, предоплату — из условий оплаты, сроки отмены — из правил отмены (снимок замораживается в заказе). То есть «единые правила наследования» из раздела 1 фактически разные у трёх семейств. — нужно решение: должны ли три семейства вести себя одинаково. \ BookingRuleSetRepository.cs:240-245; CancelRuleRepository.cs:244-245 и откат к сфере в GetCancelRuleOrDefaultByBookingConditionsQueryHandler.cs:74-84; PaymentFiltersReadOnlyRepository.cs:233,270 (приоритеты 3/2), :500-501 (уровень партнёрской зоны только для веб-оплаты на месте); потребление в заказах — CreateOrderCommandHandler.cs:416-430, CreateOrderPaymentCommandHandler.cs:211-222Бизнес/РазработкаOpen(А, рекоменд.) привести три семейства к одному описанному алгоритму подбора и зафиксировать его в BR2.4-2 как единое правило — сейчас партнёр не может предсказать поведение системы, оно зависит от того, какое правило он настраивает. (Б) признать различия намеренными и описать в BRD по каждому семейству отдельно, тогда формулировку «для всех правил работы с заказами должна действовать система наследования» нужно смягчить. Связать с OQ2.4-10.Нужно подтвердить с бизнесом, должны ли условия создания, условия оплаты и правила отмены работать по одной общей логике наследования. Сейчас они ведут себя по-разному, и это может быть как осознанным правилом, так и расхождением в реализации. Если различия нужны, описать в BRD отдельную логику для каждого семейства правил. Если нужна единая логика, завести отдельную доработку на выравнивание поведения: она затронет все три семейства правил и потребителей в заказах, поэтому требует оценки разработки.
OQ2.4-7Код BR2.4-1Требование говорит: параметры определяют условия и формат работы с бронированиями в процессинговых статусах. В коде такого термина нет — ни поля, ни перечисления, поиск по монорепо совпадений не даёт, и наборы правил со статусом заказа нигде не сопоставляются. Связь со статусом есть, но совсем другая и в другом месте: правила проверяются один раз при расчёте заказа, нарушение возвращается как «мягкая» ошибка расчёта и не прерывает создание — заказ создаётся с сохранёнными в нём ошибками. Жёсткая блокировка срабатывает только для одного статуса: если заказ создаётся сразу как «Зарезервировано», при наличии ошибок бросается отказ. Для всех остальных статусов заказ с нарушенными правилами создать можно. — нужно решение: для каких статусов нарушение правил должно блокировать заказ. \ CreateOrderCommandHandler.cs:348-351 (блокировка только для статуса «Зарезервировано»), CalculationService.cs:357,457-459 (нарушение — мягкая ошибка, расчёт не прерывается), OrderModel.cs:55 (ошибки сохраняются в заказе); поиск ProcessingStatus/ProcessStatus по монорепо — совпадений нетБизнес (Герман)Open(А, рекоменд.) заменить в BRD «в процессинговых статусах» на фактическую модель — явно перечислить статусы, в которых нарушение правил блокирует заказ, и подтвердить, что в остальных заказ создаётся с зафиксированными нарушениями. Сейчас термин непроверяем, а реальное поведение (заказ в обход правил) в требованиях не описано вообще. (Б) если блокировать нужно всегда — это изменение поведения сервиса заказов, заводить отдельно.Нужно подтвердить с бизнесом: если заказ нарушает правила бронирования, система должна всегда запрещать его создание или запрет нужен только для отдельных статусов, например для «Зарезервировано». Если для части статусов заказ можно создать с ошибками, эти статусы нужно явно перечислить в BRD. Если нарушение правил должно блокировать заказ всегда, нужна отдельная доработка сервиса заказов.
OQ2.4-8Код BR2.4-1Проблема: два из трёх видов проверок создания заказа фактически не работают. В обработчике проверки «можно ли забронировать» блок «бронирование день в день отключено» и блок «минимальная длительность заказа» целиком обёрнуты в условие if (request.IgnoreBookingRules) — то есть выполняются только когда запрошено игнорировать правила, и пропускаются при обычном бронировании. Флаг перепутан местами. Внутри блока минимальной длительности есть ещё и недостижимая ветка (durationHours < ... && !request.IgnoreBookingRules внутри ветки, где флаг уже истинен). При этом ни в одном месте кода флаг не выставляется в «истина», а создание заказа передаёт его жёстко как «ложь». Итог: запрет брони день в день и минимальная длительность заказа не проверяются ни на одном рабочем пути, хотя минимальная длительность объявлена в 2.4.1 обязательным системным правилом. Проверки «часов до начала», «строгих промежутков» и покрытия рабочими часами этим не задеты — они выполняются всегда. \ BookingAllowedQueryHandler.cs:88-98 (день в день), :221-275 (минимальная длительность), :264 (недостижимая ветка), CreateOrderCommandHandler.cs:363 и CreateOrderWidgetCommandHandler.cs:363 (флаг всегда «ложь»); поиск присваивания флага «истина» по монорепо — совпадений нетРазработка (Владислав)Закрывает PMЗакрываю сам: завести дефект «инвертирован флаг игнорирования правил бронирования: минимальная длительность и запрет брони день в день не проверяются» с указанием строк и с выяснением, зачем флаг вводился (миграция 20260206143115_AddedIgnoreBookingRule в сервисе заказов) → тикет в Bitrix. Продуктового выбора нет: правила объявлены обязательными, поведение — ошибка. Детальная сверка самих правил — в прогоне по Back 2.4.1 Условия создания.Завести дефект в разработку: исправить инверсию IgnoreBookingRules, чтобы при обычном бронировании проверялись запрет брони день в день и минимальная длительность заказа. Дополнительно проверить сценарии, где правила действительно должны игнорироваться.
OQ2.4-9Код BR2.4-2Проблема: во втором способе чтения правил (GetByBaseOrRoomId) ветка «по площадке» — дословная копия ветки «по объекту»: фильтр строится по объекту, а идентификатор площадки в условие не попадает. Подтверждено на текущем состоянии кода. Уточнение по сравнению со сверкой Back 2.2: единственный потребитель этого метода — отвязка правил при смене рабочих часов, и он вызывается из двух мест. При смене часов площадки идентификатор объекта передаётся пустым, поэтому условие никогда не выполняется и запрос возвращает пусто — правила, привязанные к площадке, при смене её часов не отвязываются никогда и продолжают действовать, перебивая правила объекта. Путь «смена часов объекта» не задет: там ветка площадки не выполняется. \ BookingRuleSetRepository.cs:124-129 (строка 126 идентична строке 120); потребитель — DeleteBaseOrRoomFromRuleSetsCommand.cs:31, вызовы — RoomHoursChangedPartnerZoneConsumer.cs:30, BaseHoursChangedPartnerZoneConsumer.cs:43Разработка (Владислав)Закрывает PMЗакрываю сам: тот же дефект, что заведён как OQ2.2-17 в сверке Back 2.2 — дополнить тикет установленным следствием (при смене часов площадки её правила не отвязываются) и списком вызовов → тикет в Bitrix. Продуктового выбора нет.Завести дефект в разработку: исправить фильтр в GetByBaseOrRoomId, чтобы ветка поиска по площадке использовала RoomId. Дополнить тикет OQ2.2-17 последствием: при смене часов площадки её правила не отвязываются и продолжают перебивать правила объекта.
OQ2.4-10Код BR2.4-2Требование говорит: сервисные правила действуют на всю систему, то есть какое-то правило есть всегда. В коде для условий создания запасного варианта нет, и разные части системы ведут себя при отсутствии правил по-разному: проверка «можно ли забронировать» отклоняет бронь с текстом «Правила бронирования не настроены для данной площадки»; пересчёт доступности вообще исключает такую площадку из расчёта (нет правил — нет свободных слотов); а мобильный поиск слотов, наоборот, просто не применяет правила и показывает время как доступное. У правил отмены поведение третье: там при ненайденном правиле система откатывается к эталону сферы. Требование не описывает, что должно происходить при отсутствии правил. — нужно решение: блокировать, показывать или применять сервисный эталон. \ BookingAllowedQueryHandler.cs:59-64 (отказ), RoomAvailabilityRecalculationWorker.cs:110-122 (площадка исключена из доступности), SearchTimeSlotsCalculation.cs:304-307,413-415 (правила просто не применяются), для сравнения — откат к эталону сферы в GetCancelRuleOrDefaultByBookingConditionsQueryHandler.cs:74-84Бизнес (Герман)Open(А, рекоменд.) сделать поведение единым и, по образцу правил отмены, откатываться к эталону сферы — тогда обещание «сервисные правила действуют на всю систему» станет правдой, площадка не сможет остаться непродаваемой из-за несозданной копии, и поиск перестанет показывать время, которое нельзя забронировать. (Б) оставить жёсткий отказ, но тогда обязательно выровнять мобильный поиск — сейчас он расходится с проверкой брони, и клиент видит слот, который получит отказ. Связать с OQ2.4-3, OQ2.4-6.Нужно решить, что делаем, если для площадки или объекта не настроены свои правила. Предлагаемый вариант — брать сервисные правила по умолчанию, чтобы поиск и создание заказа работали одинаково. Если выбираем блокировку, нужно также скрывать такие слоты в поиске, чтобы пользователь не видел время, которое потом нельзя забронировать.
OQ2.4-11Код BR2.4-2Требование говорит: сервисные правила наследуются в настройки, то есть копия должна создаваться один раз и предсказуемо. В коде защита от повторного копирования опирается на недокументированное условие: при поиске уже созданных копий отбираются только те наборы, у которых дата изменения строго больше даты создания, — то есть «только те, что уже редактировали». Но при создании набора обе даты выставляются двумя отдельными обращениями к системным часам, поэтому для свежей копии это условие срабатывает непредсказуемо (зависит от точности таймера). Из-за этого проверка «копия из этого эталона уже есть» может не сработать и создать дубль. Тот же приём влияет и на удаление созданных из эталона правил. Уникальность привязок в базе проверить нельзя — миграций и SQL в сервисе нет. Такое же условие продублировано в правилах отмены. \ BookingRuleSetRepository.cs:143-150, CreateFromDefaultCommandHandler.cs:60-61, BookingRuleSetAggregate.cs:127 (обе даты — раздельные вызовы часов); тот же приём — CancelRuleRepository.cs:320,337Разработка (Владислав)Open(А, рекоменд.) искать созданные копии по явной ссылке на эталон, не привязываясь к датам, и закрыть дубли ограничением уникальности в базе — сейчас защита работает случайно. (Б) как минимум выставлять дату создания и дату изменения одним значением, чтобы условие стало детерминированным, — это полумера, дубли по гонке останутся.Завести задачу в разработку: заменить определение копий из эталона по датам на явную связь с исходным эталоном и добавить защиту от дублей. Как минимум выставлять CreatedAt и UpdatedAt одним значением, но целевое решение — не использовать даты как признак копии.
OQ2.4-12Код BR2.4-2Требование говорит: правила уточняются привязкой к сущностям — подразумевается, что для сущности определён ровно один действующий набор. В коде ничего не мешает привязать к одной площадке несколько наборов: подбор упорядочивает кандидатов только по уровню (площадка выше объекта) и берёт первый, без дополнительного признака старшинства — ни по дате создания, ни по чему-либо ещё. При двух наборах одного уровня победитель не определён и может меняться между запросами. Отдельно: период действия набора (даты «с» и «по») при подборе и при применении не проверяется вообще — набор с истёкшим периодом продолжает участвовать наравне с действующим. \ BookingRuleSetRepository.cs:240-245 (нет разрешения ничьей и нет фильтра по периоду), BookingAllowedQueryHandler.cs:32-293 (обращений к периоду действия нет); само поле — BookingRuleSet.cs:30-34Бизнес/РазработкаOpen(А, рекоменд.) добавить фильтр по периоду действия и явное правило разрешения ничьей (например, более поздний по дате создания) — сейчас поведение недетерминированное, а заявленный в модели период фактически декоративен. (Б) запретить несколько наборов на одну сущность ограничением в базе — надёжнее, но требует разбора уже накопленных данных. Связать с OQ2.4-11.Нужно подтвердить с бизнесом простое правило: у одной сущности должен быть один действующий набор правил или можно заводить несколько наборов с разными периодами. Рекомендация — оставить один действующий набор на сущность в один момент времени, а будущие периоды разрешить только без пересечений. После подтверждения доработать подбор правил: учитывать период действия и не допускать неоднозначного выбора набора.
OQ2.4-13Код BR2.4-2Требование говорит: привязка правил определяется в том числе партнёрской зоной. В коде результат подбора правил кэшируется по паре «площадка + объект», партнёрская зона в ключ кэша намеренно не включена (это зафиксировано комментарием в самом коде). Пока идентификаторы площадок и объектов уникальны в пределах системы, ошибки не будет, но защиты от пересечения между партнёрскими зонами на уровне ключа нет. Сбрасывается кэш по меткам площадки и объекта. \ BookingRuleSetRepository.cs:202-203, CacheKeys.cs:16Разработка (Владислав)Open(А, рекоменд.) добавить партнёрскую зону в ключ кэша — цена изменения минимальна, риск пересечения устраняется. (Б) оставить как есть и зафиксировать в коде явное обоснование (глобальная уникальность идентификаторов) — допустимо, но тогда это архитектурное допущение должно быть записано. Вопрос отмечен и в сверке Back 2.2 (в отрезанных находках), здесь заведён по существу.Добавить PartnerZoneId в ключ кэша подбора правил, чтобы исключить пересечения между разными партнёрскими зонами.
OQ2.4-14Код вне BRDЧто нашли: операция, которая отвязывает объект или площадку от наборов правил, выполняется без какой-либо проверки прав — в отличие от всех остальных операций над правилами, где права проверяются (booking_rules_write, при архивации дополнительно booking_rules_delete). Наружу она не опубликована и вызывается только внутренними обработчиками событий, поэтому прямой угрозы сейчас нет, но защита держится исключительно на том, что метод не выставлен в интерфейс. В том же обработчике перехват ошибки не откатывает транзакцию, хотя во всех соседних обработчиках откат есть. \ DeleteBaseOrRoomFromRuleSetsCommand.cs:15-47 (нет проверки прав), :43-46 (перехват без отката); для сравнения — UpdateRuleSetCommandHandler.cs:119-125Разработка (Владислав)Open(А, рекоменд.) добавить проверку прав и откат транзакции — приводит операцию к общему для сервиса образцу, цена минимальна. (Б) если операция принципиально служебная, явно пометить её как внутреннюю и закрыть от публикации, чтобы отсутствие проверки было осознанным решением, а не случайностью.Реализовать откат транзакции в случае ошибки. Проверку прав не добавлять в старой реализации, пока команда остаётся внутренней; если ручка будет опубликована наружу, проверка доступа должна выполняться через ABAC.
OQ2.4-15Код вне BRDЧто нашли: события об изменении набора правил, по которым другие части системы узнают об изменениях, передают только один вид правил из трёх — «строгие промежутки». Правила «минимальная длительность» и «часов до начала» в передаваемых данных отсутствуют, хотя событие заявлено как «текущее состояние набора». Сейчас последствий нет: внутри сервиса события используются только для сброса кэша, а единственный внешний подписчик — сервис цен — реагирует именно на строгие промежутки и отвязывает цены. Но для любого будущего подписчика картина набора будет неполной. \ BookingRuleEventDto.cs:12-23 (состав передаваемых данных), BookingRuleSetAggregate.cs:324-339 (сборка данных), подписчик — BookingRuleChangedConsumer.cs:34-56 в booking.pricesБизнес/РазработкаOpen(А, рекоменд.) дополнить данные события недостающими видами правил — сейчас событие называется «текущее состояние», но состоянием не является, и это ловушка для будущего потребителя. (Б) переименовать событие и явно описать, что оно служит сигналом к сбросу кэша и к отвязке цен.Нужно подтвердить с бизнесом/архитектурой назначение события: это полный снимок набора правил или только сигнал об изменении. Если событие не должно содержать полный набор правил, переименовать DTO/событие и явно зафиксировать в контракте, что оно не является источником всех правил. Полный снимок реализовывать отдельным событием/DTO только при появлении такой потребности. Если событие должно быть полным снимком, доработать DTO и добавить все виды правил.
OQ2.4-16Код вне BRDЧто нашли: правила хранятся дважды по схеме. Фактически все три вида правил лежат внутри строки набора в виде трёх JSON-полей, и только они читаются и пишутся. При этом при инициализации базы по-прежнему создаются старые нормализованные таблицы под строгие промежутки, их часы и правила «часов до начала» — в самом коде помечено «устарело, теперь правила в JSON». Эти таблицы не участвуют ни в чтении, ни в записи. \ BookingRuleSet.cs:61-69 (три JSON-поля), DbInitializer.cs:81 (пометка «устарело»), :82-84 (устаревшие таблицы всё ещё создаются), RuleSetMapper.cs:85-201 (маппинг только через JSON)Разработка (Владислав)Закрывает PMЗакрываю сам: завести задачу на уборку — убрать создание устаревших таблиц и, после проверки, что данных в них нет, удалить их → тикет в Bitrix. Продуктового выбора нет, на поведение не влияет, но вводит в заблуждение при чтении схемы.Завести техническую задачу: проверить, что в устаревших нормализованных таблицах нет используемых данных, после этого убрать их создание из DbInitializer и удалить сами таблицы. Текущее хранение правил оставить через JSON-поля набора правил.
OQ2.4-17Код BR2.4-2Проблема (в документации, не в коде): комментарий к требованию отсылает за стандартными сервисными правилами к разделу Back 8.4 Параметры системы, но этот раздел — пустая страница-оглавление без собственного текста и без единого требования (в нём только подстраницы про сервисные промокоды, балльную систему и скрипты — к правилам работы с заказами они отношения не имеют). Источник «стандартных правил», на который опирается вся модель наследования, нигде не описан, поэтому проверить его соответствие коду нечем. \ 8. Администрирование/8.4 Параметры системы/README.md — «Страница-раздел без собственного текста в вики»Закрывает PMЗакрываю сам: либо описать в 8.4 сервисные эталоны правил работы с заказами, либо переадресовать ссылку на раздел, где они действительно описаны → правка BRD. Пока раздел пуст, требование BR2.4-2 опирается на несуществующий источник.
OQ2.4-18Код BR2.4-2Что подтверждено: основа модели, ради которой раздел и написан, в коде есть и работает. Наборы правил действительно привязываются к сущностям отдельной таблицей привязок (партнёрская зона, объект, площадка), один набор может быть привязан сразу к нескольким сущностям, и при подборе набор, привязанный к площадке, имеет приоритет над набором объекта; при отсутствии правил площадки берутся правила объекта. Архивные наборы в подборе не участвуют. Та же двухуровневая приоритезация независимо реализована и для правил отмены, и для условий оплаты — принцип «площадка уточняет объект» выдержан по всем трём семействам. Копирование эталона сферы на новый объект действительно происходит автоматически при создании объекта. \ BookingRuleSetRepository.cs:240-245, :233 (архивные исключены), BookingRuleSetScope.cs:8-17; правила отмены — CancelRuleRepository.cs:244-245; условия оплаты — PaymentFiltersReadOnlyRepository.cs:233,270; автокопирование — BaseCreatedPartnerZoneConsumer.cs:73ПодтвержденоРасхождения нет. Ограничение подтверждения: подтверждены два нижних уровня и сам механизм привязки; вопросы по остальным двум уровням и по семантике «уточнения» — OQ2.4-1, OQ2.4-2, OQ2.4-3.

3 items under this folder.