Инициализировать репозиторий «Дейл»

Первый коммит: модульный монолит ядра (.NET 10) и gRPC-сервисы
ai/ml/telegram, фронтенд Vue 3/Vite/Tailwind, документация (ТЗ,
инструкция пользователя, техдокументация, код-стайл), бэклог,
скрипты развёртывания и архив прототипа LeadRadar.
This commit is contained in:
Rustam Khalimov
2026-09-11 02:50:17 +03:00
commit 9e07568ddd
1402 changed files with 177470 additions and 0 deletions
@@ -0,0 +1,65 @@
using System.Text.Json.Serialization;
namespace Deal.Modules.Pipeline.Application.Models;
/// <summary>
/// Элемент очереди входящих — item ответа GET /api/pipeline/queue (§4.5 L308, processing.list_queue L218–241).
/// </summary>
/// <remarks>
/// Поля 1:1 с §4.5 (фронт читает: id/text/status/ch/msgAt; dialogId/msgId/queuedAt — справочные). Status —
/// <c>new</c> (ждёт правил/дедупа/ML) | <c>filtered</c> (прошла «new»-проход, ждёт ИИ; в счётчиках — bucket
/// «ai»). Времена наружу epoch-ms; маппинг с DateTimeOffset-строкой (Ruling 1) выполняет адаптер хранилища.
/// <see cref="Force"/> — внутренний флаг строки «возвращено из отсева» (Ruling 2/8), в JSON не выходит
/// ([JsonIgnore]): прототипная запись pipeline_msg несёт force, но wire очередь её не отдаёт.
/// </remarks>
public sealed record QueueItemDto
{
/// <summary>
/// Короткий id строки очереди (префикс <c>p_</c>, Ruling 10).
/// </summary>
public string Id { get; init; } = string.Empty;
/// <summary>
/// Id диалога-источника сообщения.
/// </summary>
public string DialogId { get; init; } = string.Empty;
/// <summary>
/// Id исходного сообщения в Telegram (дубль-гвард приёма), либо null.
/// </summary>
public long? MsgId { get; init; }
/// <summary>
/// Текст сообщения (обрезан при приёме до 6000 символов, Ruling 2).
/// </summary>
public string Text { get; init; } = string.Empty;
/// <summary>
/// Статус строки: <c>new</c> | <c>filtered</c> (значения — как pipeline.py ST_NEW/ST_AI).
/// </summary>
public string Status { get; init; } = string.Empty;
/// <summary>
/// Канал-источник (выходит под ключом <c>ch</c>).
/// </summary>
[property: JsonPropertyName("ch")]
public PipelineChannelDto Channel { get; init; } = new(string.Empty, string.Empty, string.Empty);
/// <summary>
/// Время исходного сообщения, epoch-ms (выходит под ключом <c>msgAt</c>).
/// </summary>
[property: JsonPropertyName("msgAt")]
public long MsgAtMs { get; init; }
/// <summary>
/// Время постановки в очередь (= CreatedAt строки), epoch-ms (выходит под ключом <c>queuedAt</c>).
/// </summary>
[property: JsonPropertyName("queuedAt")]
public long QueuedAtMs { get; init; }
/// <summary>
/// Внутренний флаг «возвращено пользователем из отсева»: правила/устарело/ML для строки игнорируются (Ruling 2/8).
/// </summary>
[JsonIgnore]
public bool Force { get; init; }
}