Merge feat/keycloak into add_filters with manual conflict resolution.
Preserve Keycloak auth/RBAC contracts while retaining filter behavior and generator consistency for future regenerations. Made-with: Cursor
This commit is contained in:
236
domain/TOiR.domain.dsl
Normal file
236
domain/TOiR.domain.dsl
Normal file
@@ -0,0 +1,236 @@
|
||||
/*
|
||||
КИС ТОиР — демонстрационная схема доменной модели
|
||||
Сущности: Equipment (Оборудование), EquipmentType (Вид оборудования), RepairOrder (Заявка на ремонт)
|
||||
*/
|
||||
|
||||
enum EquipmentStatus {
|
||||
value Active {
|
||||
label "В эксплуатации";
|
||||
}
|
||||
value Repair {
|
||||
label "В ремонте";
|
||||
}
|
||||
value Reserve {
|
||||
label "В резерве";
|
||||
}
|
||||
value WriteOff {
|
||||
label "Списано";
|
||||
}
|
||||
}
|
||||
|
||||
enum RepairKind {
|
||||
value TO {
|
||||
label "Техническое обслуживание";
|
||||
}
|
||||
value TR {
|
||||
label "Текущий ремонт";
|
||||
}
|
||||
value TRE {
|
||||
label "Текущий расширенный ремонт";
|
||||
}
|
||||
value KR {
|
||||
label "Капитальный ремонт";
|
||||
}
|
||||
value AR {
|
||||
label "Аварийный ремонт";
|
||||
}
|
||||
value MP {
|
||||
label "Метрологическая поверка";
|
||||
}
|
||||
}
|
||||
|
||||
enum RepairOrderStatus {
|
||||
value Draft {
|
||||
label "Черновик";
|
||||
}
|
||||
value Approved {
|
||||
label "Утверждена";
|
||||
}
|
||||
value InWork {
|
||||
label "В работе";
|
||||
}
|
||||
value Done {
|
||||
label "Выполнена";
|
||||
}
|
||||
value Cancelled {
|
||||
label "Отменена";
|
||||
}
|
||||
}
|
||||
|
||||
entity EquipmentType {
|
||||
description "Вид (марка) оборудования — нормативный справочник НСИ";
|
||||
|
||||
attribute code {
|
||||
key primary;
|
||||
description "Код вида оборудования";
|
||||
type string;
|
||||
is required;
|
||||
is unique;
|
||||
}
|
||||
|
||||
attribute name {
|
||||
description "Наименование вида";
|
||||
type string;
|
||||
is required;
|
||||
}
|
||||
|
||||
attribute manufacturer {
|
||||
description "Производитель";
|
||||
type string;
|
||||
}
|
||||
|
||||
attribute maintenanceIntervalHours {
|
||||
description "Периодичность ТО, моточасов";
|
||||
type integer;
|
||||
}
|
||||
|
||||
attribute overhaulIntervalHours {
|
||||
description "Периодичность КР, моточасов";
|
||||
type integer;
|
||||
}
|
||||
}
|
||||
|
||||
entity Equipment {
|
||||
description "Единица оборудования — объект ремонта и технического обслуживания";
|
||||
|
||||
attribute id {
|
||||
type uuid;
|
||||
key primary;
|
||||
}
|
||||
|
||||
attribute inventoryNumber {
|
||||
description "Инвентарный номер";
|
||||
type string;
|
||||
is required;
|
||||
is unique;
|
||||
}
|
||||
|
||||
attribute serialNumber {
|
||||
description "Заводской (серийный) номер";
|
||||
type string;
|
||||
}
|
||||
|
||||
attribute name {
|
||||
description "Наименование единицы оборудования";
|
||||
type string;
|
||||
is required;
|
||||
}
|
||||
|
||||
attribute equipmentTypeCode {
|
||||
type string;
|
||||
key foreign {
|
||||
relates EquipmentType.code;
|
||||
}
|
||||
is required;
|
||||
}
|
||||
|
||||
attribute status {
|
||||
description "Текущий статус";
|
||||
type EquipmentStatus;
|
||||
default Active;
|
||||
is required;
|
||||
}
|
||||
|
||||
attribute location {
|
||||
description "Место эксплуатации / скважина / куст";
|
||||
type string;
|
||||
}
|
||||
|
||||
attribute commissionedAt {
|
||||
description "Дата ввода в эксплуатацию";
|
||||
type date;
|
||||
}
|
||||
|
||||
attribute totalEngineHours {
|
||||
description "Общая наработка, моточасов";
|
||||
type decimal;
|
||||
}
|
||||
|
||||
attribute engineHoursSinceLastRepair {
|
||||
description "Наработка с последнего ремонта, моточасов";
|
||||
type decimal;
|
||||
}
|
||||
|
||||
attribute lastRepairAt {
|
||||
description "Дата последнего ремонта";
|
||||
type date;
|
||||
}
|
||||
|
||||
attribute notes {
|
||||
description "Примечания";
|
||||
type text;
|
||||
}
|
||||
}
|
||||
|
||||
entity RepairOrder {
|
||||
description "Заявка на ремонт — формируется по ППР или по факту обнаруженного дефекта";
|
||||
|
||||
attribute id {
|
||||
type uuid;
|
||||
key primary;
|
||||
}
|
||||
|
||||
attribute number {
|
||||
description "Номер заявки";
|
||||
type string;
|
||||
is required;
|
||||
is unique;
|
||||
}
|
||||
|
||||
attribute equipmentId {
|
||||
type uuid;
|
||||
key foreign {
|
||||
relates Equipment.id;
|
||||
}
|
||||
is required;
|
||||
}
|
||||
|
||||
attribute repairKind {
|
||||
description "Вид ремонта";
|
||||
type RepairKind;
|
||||
is required;
|
||||
}
|
||||
|
||||
attribute status {
|
||||
type RepairOrderStatus;
|
||||
default Draft;
|
||||
is required;
|
||||
}
|
||||
|
||||
attribute plannedAt {
|
||||
description "Плановая дата начала";
|
||||
type date;
|
||||
is required;
|
||||
}
|
||||
|
||||
attribute startedAt {
|
||||
description "Фактическая дата начала";
|
||||
type date;
|
||||
}
|
||||
|
||||
attribute completedAt {
|
||||
description "Фактическая дата завершения";
|
||||
type date;
|
||||
}
|
||||
|
||||
attribute contractor {
|
||||
description "Подрядная организация (если внешний ремонт)";
|
||||
type string;
|
||||
}
|
||||
|
||||
attribute engineHoursAtRepair {
|
||||
description "Наработка на момент ремонта, моточасов";
|
||||
type decimal;
|
||||
}
|
||||
|
||||
attribute description {
|
||||
description "Описание работ / дефекта";
|
||||
type text;
|
||||
}
|
||||
|
||||
attribute notes {
|
||||
description "Примечания";
|
||||
type text;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,6 +1,46 @@
|
||||
# DSL Language Specification
|
||||
|
||||
This document describes the DSL (Domain Specific Language) used to specify fullstack CRUD applications. The DSL has four layers: Domain, DTO, API, and UI.
|
||||
This document describes the single DSL (Domain Specific Language) used to specify fullstack CRUD applications. The only required DSL input is `domain/*.dsl`.
|
||||
|
||||
`domain-summary.json` is a derived artifact generated from this DSL to stabilize LLM-first generation and feed the lightweight validation gate. It must never replace the DSL as the source of truth. The active prompt corpus that consumes this contract lives in `prompts/`.
|
||||
|
||||
---
|
||||
|
||||
# DSL Responsibility
|
||||
|
||||
The domain DSL defines only:
|
||||
|
||||
- domain model
|
||||
- relations
|
||||
- enums
|
||||
|
||||
The domain DSL is the single source of truth for:
|
||||
|
||||
- entities
|
||||
- attributes
|
||||
- primary keys
|
||||
- foreign keys
|
||||
- enums
|
||||
|
||||
The following layers are always derived from the domain DSL and must not be authored as standalone authoritative DSL inputs:
|
||||
|
||||
- DTO
|
||||
- API
|
||||
- UI
|
||||
|
||||
Optional extension mechanism:
|
||||
|
||||
```text
|
||||
overrides/
|
||||
api-overrides.dsl
|
||||
ui-overrides.dsl
|
||||
```
|
||||
|
||||
Override rules:
|
||||
|
||||
- Overrides are optional.
|
||||
- The generator must work without them.
|
||||
- Overrides may refine derived API or UI behavior, but they must not duplicate or redefine entities, attributes, primary keys, foreign keys, relations, or enums.
|
||||
|
||||
---
|
||||
|
||||
@@ -108,7 +148,7 @@ attribute equipmentTypeCode {
|
||||
|
||||
## required
|
||||
|
||||
- **is required** — attribute is non-nullable in domain and (unless overridden) in DTOs.
|
||||
- **is required** — attribute is non-nullable in the domain model and drives requiredness in derived DTO/API/UI artifacts.
|
||||
- Absence of `is required` means the attribute is optional (nullable).
|
||||
|
||||
---
|
||||
@@ -120,33 +160,6 @@ attribute equipmentTypeCode {
|
||||
|
||||
---
|
||||
|
||||
## map
|
||||
|
||||
Used in **DTO** and **UI** layers to bind a DTO/UI field to a domain entity attribute.
|
||||
|
||||
**In DTO:**
|
||||
|
||||
```
|
||||
attribute name {
|
||||
type string;
|
||||
map Equipment.name;
|
||||
}
|
||||
```
|
||||
|
||||
- Ensures DTO attribute corresponds to an existing `Entity.attribute` and that types align.
|
||||
|
||||
**In UI:**
|
||||
|
||||
```
|
||||
attribute Наименование {
|
||||
map Equipment.name;
|
||||
}
|
||||
```
|
||||
|
||||
- UI label (e.g. "Наименование") maps to domain field `Equipment.name` for correct data binding and generation.
|
||||
|
||||
---
|
||||
|
||||
# DSL → System Component Mapping
|
||||
|
||||
## DSL → Prisma
|
||||
@@ -174,9 +187,9 @@ attribute Наименование {
|
||||
| entity | One module (e.g. equipment.module.ts) |
|
||||
| entity | Controller with CRUD endpoints |
|
||||
| entity | Service with Prisma CRUD |
|
||||
| DTO (Create) | create-{entity}.dto.ts |
|
||||
| DTO (Update) | update-{entity}.dto.ts |
|
||||
| DTO (Response) | Used for GET response shape |
|
||||
| entity + attribute metadata | create-{entity}.dto.ts |
|
||||
| entity + attribute metadata | update-{entity}.dto.ts |
|
||||
| entity + attribute metadata | Response DTO / API shape |
|
||||
|
||||
API paths are derived from entity name: PascalCase → kebab-case, pluralized (e.g. `Equipment` → `/equipment`, `RepairOrder` → `/repair-orders`).
|
||||
|
||||
@@ -193,21 +206,12 @@ API paths are derived from entity name: PascalCase → kebab-case, pluralized (e
|
||||
| type date | DateInput, DateField |
|
||||
| enum | SelectInput with choices |
|
||||
| foreign key | ReferenceInput, ReferenceField |
|
||||
| UI attribute with map | Field with correct source |
|
||||
|
||||
---
|
||||
|
||||
# DTO Mapping
|
||||
# Derived Layer Mapping
|
||||
|
||||
- **map Entity.attribute** — DTO attribute corresponds to domain attribute; types must match.
|
||||
- **Create DTO** — must not include generated primary keys (e.g. no `id` for uuid PK).
|
||||
- **Update DTO** — all fields optional (nullable) for partial updates.
|
||||
- **List response DTO** — must expose `data` (array) and `total` (integer) for React Admin compatibility.
|
||||
|
||||
---
|
||||
|
||||
# UI Mapping
|
||||
|
||||
- Each UI attribute should have **map Entity.attribute** so it binds to a real domain field.
|
||||
- UI attribute name is the label (e.g. "Наименование"); **source** in generated components is the domain attribute name (e.g. `name`).
|
||||
- Enums → SelectInput; foreign keys → ReferenceInput/ReferenceField.
|
||||
- **Create DTO** — derived from domain attributes and must not include generated primary keys (for example no `id` for uuid PKs).
|
||||
- **Update DTO** — derived from the same domain attributes with all fields optional for partial updates.
|
||||
- **API response shape** — derived from domain attributes and must expose React Admin-compatible identifiers when needed.
|
||||
- **UI field mapping** — derived from attribute types, descriptions, enums, and foreign keys without a separate UI DSL.
|
||||
|
||||
Reference in New Issue
Block a user