139 lines
3.8 KiB
C#
139 lines
3.8 KiB
C#
using System.Reflection;
|
|
using Omika.Core.Observability.External;
|
|
|
|
namespace Omika.Tests.Observability.External;
|
|
|
|
/// <summary>Validation de la configuration du pont externe (§74/§75).</summary>
|
|
public class ExternalObservabilityOptionsTests
|
|
{
|
|
[Fact]
|
|
public void Default_IsDisabled_AndNotUsable()
|
|
{
|
|
var options = new ExternalObservabilityOptions();
|
|
|
|
Assert.False(options.Enabled);
|
|
Assert.False(options.IsUsable);
|
|
Assert.Empty(options.Validate());
|
|
}
|
|
|
|
[Fact]
|
|
public void Disabled_IsAlwaysValid()
|
|
{
|
|
var options = new ExternalObservabilityOptions
|
|
{
|
|
Enabled = false,
|
|
OtlpEndpoint = "",
|
|
ExportTimeoutSeconds = 0,
|
|
MaxQueueSize = 0
|
|
};
|
|
|
|
Assert.Empty(options.Validate());
|
|
}
|
|
|
|
[Fact]
|
|
public void Enabled_WithEmptyEndpoint_IsInvalid()
|
|
{
|
|
var options = new ExternalObservabilityOptions { Enabled = true, OtlpEndpoint = "" };
|
|
|
|
Assert.False(options.IsUsable);
|
|
Assert.NotEmpty(options.Validate());
|
|
}
|
|
|
|
[Fact]
|
|
public void Enabled_WithValidHttpEndpoint_IsUsable()
|
|
{
|
|
var options = new ExternalObservabilityOptions
|
|
{
|
|
Enabled = true,
|
|
OtlpEndpoint = "http://10.0.0.10:4318"
|
|
};
|
|
|
|
Assert.True(options.IsUsable);
|
|
Assert.Empty(options.Validate());
|
|
}
|
|
|
|
[Fact]
|
|
public void Enabled_WithNonHttpEndpoint_IsInvalid()
|
|
{
|
|
var options = new ExternalObservabilityOptions
|
|
{
|
|
Enabled = true,
|
|
OtlpEndpoint = "ftp://collector:4318"
|
|
};
|
|
|
|
Assert.False(options.IsUsable);
|
|
Assert.Contains(options.Validate(), e => e.Contains("http", StringComparison.OrdinalIgnoreCase));
|
|
}
|
|
|
|
[Theory]
|
|
[InlineData(0)]
|
|
[InlineData(61)]
|
|
public void ExportTimeoutSeconds_MustBeBetween1And60(int value)
|
|
{
|
|
var options = new ExternalObservabilityOptions
|
|
{
|
|
Enabled = true,
|
|
OtlpEndpoint = "http://localhost:4318",
|
|
ExportTimeoutSeconds = value
|
|
};
|
|
|
|
Assert.False(options.IsUsable);
|
|
}
|
|
|
|
[Theory]
|
|
[InlineData(0)]
|
|
[InlineData(-1)]
|
|
public void NonPositiveBounds_AreInvalid(int value)
|
|
{
|
|
var options = new ExternalObservabilityOptions
|
|
{
|
|
Enabled = true,
|
|
OtlpEndpoint = "http://localhost:4318",
|
|
MaxQueueSize = value
|
|
};
|
|
|
|
Assert.False(options.IsUsable);
|
|
}
|
|
|
|
[Fact]
|
|
public void TwoInstances_AreIndependent_NoSharedStaticState()
|
|
{
|
|
var a = new ExternalObservabilityOptions
|
|
{
|
|
Enabled = true,
|
|
OtlpEndpoint = "http://a:4318",
|
|
MaxQueueSize = 111
|
|
};
|
|
var b = new ExternalObservabilityOptions
|
|
{
|
|
Enabled = false,
|
|
OtlpEndpoint = "http://b:4318",
|
|
MaxQueueSize = 222
|
|
};
|
|
|
|
// Chaque instance conserve ses propres valeurs (aucune contamination croisée,
|
|
// aucun état statique mutable partagé).
|
|
Assert.True(a.Enabled);
|
|
Assert.Equal("http://a:4318", a.OtlpEndpoint);
|
|
Assert.Equal(111, a.MaxQueueSize);
|
|
|
|
Assert.False(b.Enabled);
|
|
Assert.Equal("http://b:4318", b.OtlpEndpoint);
|
|
Assert.Equal(222, b.MaxQueueSize);
|
|
}
|
|
|
|
[Fact]
|
|
public void Options_HasNoStaticMutableState()
|
|
{
|
|
// Garde-fou anti-régression (§13/§28) : la config du pont externe ne doit
|
|
// être pilotée par AUCUN champ static mutable (DI-friendly, isolable, testable).
|
|
string[] staticMutable = typeof(ExternalObservabilityOptions)
|
|
.GetFields(BindingFlags.Public | BindingFlags.NonPublic | BindingFlags.Static)
|
|
.Where(f => !f.IsInitOnly && !f.IsLiteral)
|
|
.Select(f => f.Name)
|
|
.ToArray();
|
|
|
|
Assert.Empty(staticMutable);
|
|
}
|
|
}
|