using Microsoft.Extensions.Diagnostics.HealthChecks;

namespace ZB.MOM.WW.Health.Akka;

/// <summary>
/// Configures how <see cref="ActiveNodeHealthCheck"/> decides which role's active node this node is
/// competing to be.
/// </summary>
public sealed class ActiveNodeHealthCheckOptions
{
    /// <summary>
    /// Candidate roles in descending precedence. The check answers for the first one the local node
    /// carries. Empty (the default) means unscoped: the active node is the oldest Up member of the
    /// whole cluster.
    /// </summary>
    /// <remarks>
    /// A fused node should list the role its singletons are pinned to first — e.g.
    /// <c>["admin", "driver"]</c> for a node that hosts the admin singletons when fused and competes
    /// as a plain driver when it is a driver-only node.
    /// </remarks>
    public IReadOnlyList<string> RolePreference { get; init; } = Array.Empty<string>();

    /// <summary>
    /// The status to report when <see cref="RolePreference"/> is non-empty and the node carries none
    /// of those roles — it owns no active work at all. Defaults to
    /// <see cref="HealthStatus.Unhealthy"/>.
    /// </summary>
    /// <remarks>
    /// Unhealthy is the safe default and is deliberately <b>not</b> the "not applicable ⇒ Healthy"
    /// convention used by readiness probes. The active tier exists so a load balancer can pick
    /// exactly one node; a node that owns no active work must not be in that pool. Answering Healthy
    /// there is what made the previous role-filtered check report 200 on every node and silently
    /// broke leader-pinning (lmxopcua#494). Override only when a node genuinely should stay in the
    /// active pool without holding any of the preferred roles.
    /// </remarks>
    public HealthStatus NoActiveRoleStatus { get; init; } = HealthStatus.Unhealthy;
}
