Endpoint: ClassifyFrame

API-контракт Версия: 0.1 draft

Опознание формы и страницы кадра: по эталонным профилям детектор относит кадр к форме/странице и возвращает уверенность и ближайшие альтернативы. Основной запуск — автоматический в фоновой очереди (ADR-014); endpoint — ручной повтор/инспекция. Поведение — ClassifyFrameHandler.

⟨/⟩ Исходник

1. Транспорт

Параметры — в пути, тела запроса нет. Ответ — единая обёртка со сводкой по кадрам (форма, страница, уверенность, альтернативы).

Штатно опознание выполняет фоновая очередь автоматически (ADR-014): результат уже готов к моменту, когда пакет берёт оператор. Этот endpoint — ручной повтор (после пересъёмки/правки состава кадров) и инспекция результата; окончательное слово за оператором (выбор формы вручную авторитетнее детектора, ADR-015).

2. Command

/// <summary>Команда опознания: `FrameOrder` задан — один кадр; null — все кадры пакета.</summary>
public class ClassifyFrameCommand : BasedCommand
{
    public Guid PacketId { get; init; }

    /// <summary>Порядковый номер кадра; null — опознать все кадры.</summary>
    public int? FrameOrder { get; init; }
}

3. Result

/// <summary>Результат опознания (обёртка + сводка по кадрам).</summary>
public class ClassifyFrameResult : BasedResult
{
    public ClassifiedPacketPayload? Payload { get; init; }
}

4. Payload

/// <summary>Итог: сколько кадров опознано/не опознано и результат по каждому.</summary>
public class ClassifiedPacketPayload
{
    public Guid PacketId { get; init; }
    public int Recognized { get; init; }
    public int Unrecognized { get; init; }
    public ClassifiedFrameInfo[] Frames { get; init; } = new ClassifiedFrameInfo[0];
}

5. FrameInfo

/// <summary>Результат опознания одного кадра.</summary>
public class ClassifiedFrameInfo
{
    public int Order { get; init; }

    /// <summary>Опознанная форма; null — вид не опознан.</summary>
    public Guid? FormId { get; init; }

    /// <summary>Наименование опознанной формы; null — вид не опознан.</summary>
    public string? FormName { get; init; }

    /// <summary>Номер страницы опознанной формы; null — вид не опознан.</summary>
    public int? PageNumber { get; init; }

    /// <summary>Уверенность — отрыв лучшего кандидата от второго места (больше = увереннее).</summary>
    public double Confidence { get; init; }

    /// <summary>Ближайшие альтернативы (для ручного выбора оператором при низкой уверенности).</summary>
    public FormCandidate[] Alternatives { get; init; } = new FormCandidate[0];

    /// <summary>Причина, если вид не опознан (нет подходящей формы / уверенность ниже порога); null — успех.</summary>
    public string? Error { get; init; }
}

6. Candidate

/// <summary>Кандидат опознания: форма, страница и её оценка соответствия (меньше — ближе).</summary>
public class FormCandidate
{
    public Guid FormId { get; init; }
    public string FormName { get; init; } = "";
    public int PageNumber { get; init; }
    public double Score { get; init; }
}