using Shouldly; using Xunit; using ZB.MOM.WW.OtOpcUa.Host.Configuration; using ZB.MOM.WW.OtOpcUa.Security.Ldap; namespace ZB.MOM.WW.OtOpcUa.Host.IntegrationTests; /// /// Task 3 — verifies the net-new (built on the shared /// ZB.MOM.WW.Configuration OptionsValidatorBase/ValidationBuilder) gates on /// , and that when enabled it requires Server, /// SearchBase, and a valid Port. Failure messages carry the real "Ldap:" /// section prefix so they read correctly when surfaced at host startup. /// public sealed class LdapOptionsValidatorTests { private static readonly LdapOptionsValidator Sut = new(); /// Valid enabled options pass validation. [Fact] public void Valid_enabled_options_succeed() { var options = new LdapOptions { Enabled = true, Server = "ldap", SearchBase = "dc=x", Port = 389, }; Sut.Validate(null, options).Succeeded.ShouldBeTrue(); } /// When LDAP is disabled all checks are skipped, so a blank config still passes. [Fact] public void Disabled_options_succeed_even_when_blank() { var options = new LdapOptions { Enabled = false, Server = string.Empty, SearchBase = string.Empty, Port = 0, }; Sut.Validate(null, options).Succeeded.ShouldBeTrue(); } /// /// When the dev stub is active the real LDAP fields are irrelevant (the bind is bypassed), so /// the gate skips the Server/SearchBase/Port checks even though LDAP is nominally enabled. /// [Fact] public void DevStubMode_options_succeed_even_when_server_blank() { var options = new LdapOptions { Enabled = true, DevStubMode = true, Server = string.Empty, SearchBase = string.Empty, Port = 0, }; Sut.Validate(null, options).Succeeded.ShouldBeTrue(); } /// Enabled with a blank server reports the required-server failure. [Fact] public void Enabled_with_blank_server_fails() { var options = new LdapOptions { Enabled = true, Server = string.Empty, SearchBase = "dc=x", Port = 389, }; var result = Sut.Validate(null, options); result.Failed.ShouldBeTrue(); result.Failures.ShouldContain("Ldap:Server is required when LDAP login is enabled."); } /// Enabled with a blank search base reports the required-search-base failure. [Fact] public void Enabled_with_blank_search_base_fails() { var options = new LdapOptions { Enabled = true, Server = "ldap", SearchBase = string.Empty, Port = 389, }; var result = Sut.Validate(null, options); result.Failed.ShouldBeTrue(); result.Failures.ShouldContain("Ldap:SearchBase is required when LDAP login is enabled."); } /// Enabled with port 0 reports the port-range failure using the shared primitive wording. [Fact] public void Enabled_with_zero_port_fails() { var options = new LdapOptions { Enabled = true, Server = "ldap", SearchBase = "dc=x", Port = 0, }; var result = Sut.Validate(null, options); result.Failed.ShouldBeTrue(); result.Failures.ShouldContain("Ldap:Port must be between 1 and 65535 (was 0)"); } }