This commit is contained in:
2026-03-27 15:51:10 +03:00
parent 15586f9a8c
commit 51378c5d66
1234 changed files with 95644 additions and 543076 deletions
+154
View File
@@ -0,0 +1,154 @@
---
id: entity-rag-index-job
title: Сущность IndexJob
doc_type: domain_entity
domain: rag
status: draft
owner: system-analyst
source_of_truth: code
related_docs:
- arch-rag-package
- logic-rag-indexing
- entity-rag-session
- api-rag-session-job
related_code:
- src/app/modules/rag/job_store.py
- src/app/modules/rag/indexing_service.py
- src/app/modules/rag/persistence/job_repository.py
- src/app/modules/rag/persistence/schema_repository.py
entities:
- IndexJob
- RagSession
tags:
- rag
- indexing
- job
- domain-entity
---
# Сущность IndexJob
## Summary
- Domain: rag
- Purpose: представить асинхронную задачу индексации и её наблюдаемый статус.
- Entity role: operational entity для выполнения snapshot/change indexing.
- Main attributes: `index_job_id`, `rag_session_id`, `status`, `indexed_files`, `failed_files`, `cache_hit_files`, `cache_miss_files`, `error`.
- Lifecycle: `queued -> running -> done|error`.
- Invariants: job всегда принадлежит одной `RagSession`, статус хранится как enum `IndexJobStatus`.
- Related APIs: создание job косвенно через session endpoints, чтение через job status endpoint и SSE endpoint.
- Related logic: `IndexingOrchestrator`, retry, EventBus publishing.
- Source of truth: `src/app/modules/rag/job_store.py`, `src/app/modules/rag/indexing_service.py`.
## Назначение
`IndexJob` хранит технический прогресс и итог выполнения индексации. Он нужен, чтобы API модуля мог вернуть результат не синхронно, а через опрос статуса и подписку на события.
## Контекст
Job создаётся на каждую snapshot- или changes-операцию. Сервис индексации обновляет его counters и публикует события прогресса в EventBus под ключом `index_job_id`.
## Роль в доменной модели
Это операционная сущность, которая связывает пользовательский запрос на индексацию с фактическим процессом обработки файлов. Она не хранит сам индекс, но управляет прозрачностью выполнения и ошибками.
## Атрибуты
| attribute | type | required | description | constraints |
|-----------|------|----------|-------------|-------------|
| `index_job_id` | `str` | yes | уникальный идентификатор задачи | primary key, non-empty |
| `rag_session_id` | `str` | yes | ссылка на целевую RAG-сессию | non-empty |
| `status` | `IndexJobStatus` | yes | текущее состояние задачи | `queued`, `running`, `done`, `error` |
| `indexed_files` | `int` | yes | число успешно обработанных файлов | `>= 0` |
| `failed_files` | `int` | yes | число файлов с ошибками | `>= 0` |
| `cache_hit_files` | `int` | yes | число файлов, обслуженных из cache | `>= 0` |
| `cache_miss_files` | `int` | yes | число файлов, потребовавших embeddings | `>= 0` |
| `error` | `ErrorPayload \| None` | no | информация о необработанной временной ошибке после retry | optional |
## Состояния и жизненный цикл
### Основные состояния
- `queued`
- `running`
- `done`
- `error`
### Переходы состояний
1. `IndexJobStore.create` создаёт job в состоянии `queued`.
2. `IndexingOrchestrator._run_with_project_lock` переводит job в `running`.
3. Успешная индексация переводит job в `done` и заполняет counters.
4. Ошибка после исчерпания retry переводит job в `error` и заполняет `ErrorPayload`.
## Инварианты и ограничения
- Job не мигрирует между `rag_session_id`.
- Финальные counters сохраняются в БД перед публикацией terminal event.
- Ошибки уровня `TimeoutError`, `ConnectionError`, `OSError` считаются временными и оборачиваются в `index_retry_exhausted` только после retry exhaustion.
## Связи с другими сущностями
| entity | relation | description |
|--------|----------|-------------|
| `RagSession` | many-to-one | каждая задача относится к одной сессии |
| `RagDocument` | indirect | job обновляет набор документов сессии, но не владеет ими напрямую |
## Использование в системе
### Related API
- `POST /api/rag/sessions`
- `POST /api/rag/sessions/{rag_session_id}/changes`
- `GET /api/rag/sessions/{rag_session_id}/jobs/{index_job_id}`
- `GET /api/rag/sessions/{rag_session_id}/jobs/{index_job_id}/events`
### Related UI
- Прямого UI в репозитории не обнаружено.
### Related logic
- `logic-rag-indexing`
### Related integrations
- EventBus SSE stream
- PostgreSQL таблица `rag_index_jobs`
## Функциональные требования
- Job должна создаваться до запуска фоновой задачи.
- Публичный API обязан проверять принадлежность job указанной `rag_session_id`.
- Progress events должны публиковаться в формате, достаточном для фронта или внешнего клиента.
## Нефункциональные требования
### Audit / history
- `created_at` и `updated_at` сохраняются в таблице `rag_index_jobs`.
### Security
- Доступ к job опирается на проверку связи `job.rag_session_id == requested rag_session_id`.
### Observability
- SSE stream отдаёт `index_status`, `index_progress`, `terminal`.
## Связанный код
### Files
- `src/app/modules/rag/job_store.py`
- `src/app/modules/rag/indexing_service.py`
- `src/app/modules/rag/persistence/job_repository.py`
- `src/app/modules/rag/persistence/schema_repository.py`
### Symbols
- `IndexJob`
- `IndexJobStore.create`
- `IndexJobStore.get`
- `IndexJobStore.save`
- `IndexingOrchestrator._run_with_project_lock`
## Связанные документы
- `arch-rag-package`
- `logic-rag-indexing`
- `entity-rag-session`
- `api-rag-session-job`
## История изменений
| Date | Source | Changes |
|------|--------|---------|
| 2026-03-13 | code | Добавлено описание lifecycle и контракта сущности `IndexJob`. |