using ZB.MOM.WW.OtOpcUa.Core.Abstractions;
using ZB.MOM.WW.OtOpcUa.Configuration.Enums;
namespace ZB.MOM.WW.OtOpcUa.Core.Authorization;
///
/// Tri-state result of an call, per decision
/// #149. Phase 6.2 only produces and
/// ; the
/// variant exists in the model so v2.1 Explicit Deny lands without an API break. Provenance
/// carries the matched grants (or empty when not granted) for audit + the Admin UI "Probe
/// this permission" diagnostic.
///
public sealed record AuthorizationDecision(
AuthorizationVerdict Verdict,
IReadOnlyList Provenance)
{
public bool IsAllowed => Verdict == AuthorizationVerdict.Allow;
/// Convenience constructor for the common "no grants matched" outcome.
public static AuthorizationDecision NotGranted() => new(AuthorizationVerdict.NotGranted, []);
/// Allow with the list of grants that matched.
public static AuthorizationDecision Allowed(IReadOnlyList provenance)
=> new(AuthorizationVerdict.Allow, provenance);
}
/// Three-valued authorization outcome.
public enum AuthorizationVerdict
{
/// At least one grant matches the requested (operation, scope) pair.
Allow,
/// No grant matches. Phase 6.2 default — treated as deny at the OPC UA surface.
NotGranted,
/// Explicit deny grant matched. Reserved for v2.1; never produced by Phase 6.2.
Denied,
}
/// One grant that contributed to an Allow verdict — for audit / UI diagnostics.
/// LDAP group the matched grant belongs to.
/// Where in the hierarchy the grant was anchored.
/// The bitmask the grant contributed.
public sealed record MatchedGrant(
string LdapGroup,
NodeAclScopeKind Scope,
NodePermissions PermissionFlags);