refactor(commons): consolidate List element-type/coercion into AttributeValueCodec; InstanceActor + CLI reuse it (#93)
This commit is contained in:
@@ -231,4 +231,56 @@ public class AttributeValueCodecTests
|
||||
[InlineData(DataType.List, false)]
|
||||
public void IsValidElementType_MatchesScalarSet(DataType t, bool expected) =>
|
||||
Assert.Equal(expected, AttributeValueCodec.IsValidElementType(t));
|
||||
|
||||
// ── ElementClrType + CoerceEnumerable: the shared object-input coercion ──
|
||||
// entry point reused by InstanceActor (live OPC UA arrays). Distinct from the
|
||||
// string-input path in Decode (JSON elements): here elements arrive as boxed
|
||||
// CLR values and are converted via Convert.ToXxx (or parsed when string).
|
||||
|
||||
[Theory]
|
||||
[InlineData(DataType.String, typeof(string))]
|
||||
[InlineData(DataType.Int32, typeof(int))]
|
||||
[InlineData(DataType.Float, typeof(float))]
|
||||
[InlineData(DataType.Double, typeof(double))]
|
||||
[InlineData(DataType.Boolean, typeof(bool))]
|
||||
[InlineData(DataType.DateTime, typeof(DateTime))]
|
||||
public void ElementClrType_MapsEachScalar(DataType t, Type expected) =>
|
||||
Assert.Equal(expected, AttributeValueCodec.ElementClrType(t));
|
||||
|
||||
[Fact]
|
||||
public void ElementClrType_RejectsNonElementType() =>
|
||||
Assert.Throws<FormatException>(() => AttributeValueCodec.ElementClrType(DataType.List));
|
||||
|
||||
[Fact]
|
||||
public void CoerceEnumerable_BuildsTypedList()
|
||||
{
|
||||
var list = AttributeValueCodec.CoerceEnumerable(new object[] { 10, 20, 30 }, DataType.Int32);
|
||||
var typed = Assert.IsType<List<int>>(list);
|
||||
Assert.Equal(new[] { 10, 20, 30 }, typed);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void CoerceEnumerable_ConvertsMixedClrElementTypes()
|
||||
{
|
||||
// Ints and numeric strings both coerce to List<double> via Convert/parse —
|
||||
// the object-input behavior InstanceActor's MV-8 coercion depends on.
|
||||
var list = AttributeValueCodec.CoerceEnumerable(new object[] { 1, "2.5", 3.75 }, DataType.Double);
|
||||
var typed = Assert.IsType<List<double>>(list);
|
||||
Assert.Equal(new[] { 1.0, 2.5, 3.75 }, typed);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void CoerceEnumerable_DateTimeRoundtripsViaInvariantCulture()
|
||||
{
|
||||
var when = new DateTime(2026, 6, 19, 8, 30, 0, DateTimeKind.Utc);
|
||||
var list = AttributeValueCodec.CoerceEnumerable(
|
||||
new object[] { when.ToString("O", CultureInfo.InvariantCulture) }, DataType.DateTime);
|
||||
var typed = Assert.IsType<List<DateTime>>(list);
|
||||
Assert.Equal(when, typed[0]);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void CoerceEnumerable_ThrowsOnUnsupportedElementType() =>
|
||||
Assert.Throws<FormatException>(
|
||||
() => AttributeValueCodec.CoerceEnumerable(new object[] { new byte[] { 1 } }, DataType.Binary));
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user