namespace Deal.Modules.Discovery.Application; /// /// Статусы кандидата Discovery (колонка DiscCandidates.Status; discovery.py L171, api-map §4.8). /// /// /// Цепочка 1:1 с прототипом: new — найден поиском, ждёт оценки; review — оценён, ждёт решения (воркер/человек); /// joined — вступили (только mark_joined: счётчик задачи + лог join_auto/join_manual); rejected — отклонён /// (только mark_rejected: счётчик задачи + лог + чёрный список). Переводы в joined/rejected минуя mark_* — /// запрещены (discovery.py L16–18). Активные статусы (python _ACTIVE_CANDIDATE L35) запрещают повторное /// добавление источника в задачу. /// public static class DiscoveryCandidateStatuses { /// /// Найден поиском, ещё не оценён. /// public const string New = "new"; /// /// Оценён (метки/фит проставлены), ждёт вступления/решения. /// public const string Review = "review"; /// /// Вступили в источник (терминал: счётчик joined задачи). /// public const string Joined = "joined"; /// /// Отклонён и помещен в чёрный список (терминал: счётчик rejected). /// public const string Rejected = "rejected"; /// /// Статусы, при которых повторное добавление источника запрещено (python _ACTIVE_CANDIDATE L35). /// /// Статус кандидата. /// True — new/review/joined (add_candidate пропускает источник с логом skip). public static bool IsActive(string status) { return status is New or Review or Joined; } /// /// Разрешён ли перевод через set_candidate_status (python L503–504: только new/review). /// /// Запрашиваемый статус. /// True — new/review (joined/rejected выставляются только через mark_joined/mark_rejected). public static bool IsTransitionAllowed(string status) { return status is New or Review; } }