using Rugrid.Sdaid.Notation.Documents;
namespace Rugrid.Sdaid.Epas.Nts.ChangeRequests
{
/// <summary>
/// `SelectedModifications` приведена к общей инфраструктурной конвенции сущностей модуля
/// (`BaseEntity`, суррогатный `Id`) — была единственной сущностью без идентификатора, с
/// композитным ключом из двух FK. Уникальность пары (расчёт, модификация), которую раньше
/// давал сам композитный ключ, зафиксирована отдельно — без этого гарантия потерялась бы.
/// </summary>
public class DOC_CR_2026_11_03_SelectedModificationsBaseEntity : IChangeRequestDocument, IHasStructuralLinks, IFolder<NtsChangeRequestsFolder>
{
public SdaidLink[] Links => new[]
{
Rel.Uses<Rugrid.Sdaid.Epas.Nts.Domain.DOC_SelectedModifications>(),
};
public static string _refName = "CR 2026-11-03: SelectedModifications приведена к BaseEntity";
public string Name => "SelectedModifications приведена к BaseEntity";
public string Description =>
@"SelectedModifications получает суррогатный Id — как и все остальные сущности модуля (общая инфраструктурная конвенция BaseEntity), вместо композитного ключа из двух FK. Уникальность пары (VehicleCalc, VehicleModification), которую раньше обеспечивал сам композитный ключ, зафиксирована отдельно.";
public string Version => "0.2";
public string Status => "done";
public string[] Comments => new string[0];
public static string Source = """
## Источник (как есть)
`SelectedModifications` была единственной доменной сущностью модуля без `Id` —
явное архитектурное решение («строка хранит пару ключей, отдельного идентификатора и
собственных атрибутов у связи нет»), композитный первичный ключ из двух FK
(`VehicleCalc`, `VehicleModification`).
Реальная инфраструктура (`src/Common/Abstracts/BaseEntity.cs`,
`BaseEntityConfiguration<TEntity> where TEntity : BaseEntity`) устроена иначе и жёстче:
`Id` — всегда суррогатный первичный ключ (`builder.HasKey(c => c.Id)`), плюс пять
технических колонок (`CreatedDate`/`CreatedBy`/`ModifiedDate`/`ModifiedBy`/`xmin`),
которые достаются любой сущности через этот базовый класс автоматически. Проверено по
всему `Ntr.Domain` (26 сущностей через `BaseEntity`, плюс справочники через
`BaseReferenceEntity`/`BaseEnumEntity`) — ни одной сущности-связи без собственного
`Id` не найдено; альтернативной инфраструктуры под композitный ключ в проекте нет.
`Nts.Domain` (персистентный слой ЭНТС) пока не существует вовсе — для ЭНТС есть
только `Nts.Calc` (калькулятор).
""";
public static string Analysis = $"""
## Разбор
1. **`Id` — техническое решение, не бизнес-атрибут связи.**
{SdaidAnchors.RefTo<Rugrid.Sdaid.Epas.Nts.Domain.DOC_SelectedModifications>()}
по-прежнему не имеет собственных БИЗНЕС-атрибутов — только пара ссылок на `VehicleCalc`
и `VehicleModification`; добавленный `Id` не меняет это, он — следствие общей
инфраструктурной конвенции, которой подчиняются все остальные сущности модуля.
2. **Добавление `Id` само по себе — не полное решение.** Композитный ключ бесплатно
гарантировал: одна и та же модификация не может быть отобрана для одного расчёта
дважды. При замене на суррогатный `Id` эта гарантия не сохраняется автоматически —
нужна отдельно заданная уникальность пары (`VehicleCalc`, `VehicleModification`).
Это зафиксировано явно в документе («Идентификатор и уникальность»), а не оставлено
подразумеваемым.
3. **Не предмет этого CR:** собственно БД-уровень (уникальный индекс в
`Nts.Domain`/EF-конфигурации) — реализовать нечего, этого слоя для ЭНТС ещё нет;
зафиксировано как требование к будущей реализации, не как код.
""";
public static string BlastRadius = $"""
## Blast radius
### Спецификация
| Документ | Правка |
|---|---|
| `Nts/50_Domain/SelectedModifications.cs` | класс-doc и `Purpose` — убрано «нет идентификатора», добавлен раздел «Идентификатор и уникальность»; сущность `SelectedModifications` — добавлено поле `Id`; `Description` у `VehicleCalc`/`VehicleModification` — отсылка на уникальность пары |
### Вне объёма
`src/Nts.Domain` не существует — backend-реализация (EF-конфигурация, уникальный
индекс) не часть этого CR, зафиксирована как требование к будущей реализации в тексте
{SdaidAnchors.RefTo<Rugrid.Sdaid.Epas.Nts.Domain.DOC_SelectedModifications>()}.
""";
public static string Plan = """
## План
1. `SelectedModifications.cs` — правка спецификации (сделано).
2. Собрать (`dotnet build`, `build-html.cmd`) (сделано).
3. `doc` — проверка.
4. Зафиксировать «Итог».
""";
public static string Acceptance = """
## Acceptance criteria
- **AC-1.** Сущность `SelectedModifications` имеет поле `Id` (та же конвенция, что и
у остальных доменных сущностей модуля).
- **AC-2.** Документ явно фиксирует уникальность пары (`VehicleCalc`,
`VehicleModification`) как отдельное требование — не выводится из наличия `Id`.
- **AC-3.** Прозу «отдельного идентификатора... нет» убрано — не осталось
противоречащих новому состоянию утверждений.
""";
public static string Result = """
## Итог
Выполнено. `SelectedModifications` получила `Id` (та же конвенция `[DomainField(Alias
= "id", RequiredOnCreate = true, Range = "UUID", Immutable = true)]`, что у всех
остальных сущностей модуля), уникальность пары (`VehicleCalc`, `VehicleModification`)
зафиксирована явно в `Purpose`.
`doc` нашёл 1 находку: факт про `Id`/уникальность был изложен дважды (в XML-doc класса
и в `Purpose`) почти идентичными, но не идентичными формулировками — введено этой же
правкой. Исправлено: XML-doc класса сокращён до краткого назначения с отсылкой «см.
Purpose», полное изложение осталось в одном месте. Остальные проверки (структурные
связи, blast radius, согласованность атрибутов `Id` с остальными 21 сущностью модуля,
факты CR про `BaseEntity`/`Ntr.Domain`) — без находок, прецедент в реальном коде
подтверждён `doc` фактической проверкой (26/26 сущностей через `BaseEntity`).
""";
}
}