Add OPC UA array element write integration test
This commit is contained in:
@@ -363,7 +363,20 @@ namespace ZB.MOM.WW.LmxOpcUa.Host.OpcUa
|
||||
{
|
||||
try
|
||||
{
|
||||
var value = nodesToWrite[i].Value.WrappedValue.Value;
|
||||
var writeValue = nodesToWrite[i];
|
||||
var value = writeValue.Value.WrappedValue.Value;
|
||||
|
||||
if (!string.IsNullOrWhiteSpace(writeValue.IndexRange))
|
||||
{
|
||||
if (!TryApplyArrayElementWrite(tagRef, value, writeValue.IndexRange, out var updatedArray))
|
||||
{
|
||||
errors[i] = new ServiceResult(StatusCodes.BadIndexRangeInvalid);
|
||||
continue;
|
||||
}
|
||||
|
||||
value = updatedArray;
|
||||
}
|
||||
|
||||
var success = _mxAccessClient.WriteAsync(tagRef, value).GetAwaiter().GetResult();
|
||||
errors[i] = success ? ServiceResult.Good : new ServiceResult(StatusCodes.BadInternalError);
|
||||
}
|
||||
@@ -376,6 +389,53 @@ namespace ZB.MOM.WW.LmxOpcUa.Host.OpcUa
|
||||
}
|
||||
}
|
||||
|
||||
private bool TryApplyArrayElementWrite(string tagRef, object? writeValue, string indexRange, out object updatedArray)
|
||||
{
|
||||
updatedArray = null!;
|
||||
|
||||
if (!int.TryParse(indexRange, out var index) || index < 0)
|
||||
return false;
|
||||
|
||||
var currentValue = _mxAccessClient.ReadAsync(tagRef).GetAwaiter().GetResult().Value;
|
||||
if (currentValue is not Array currentArray || currentArray.Rank != 1 || index >= currentArray.Length)
|
||||
return false;
|
||||
|
||||
var nextArray = (Array)currentArray.Clone();
|
||||
var elementType = currentArray.GetType().GetElementType();
|
||||
if (elementType == null)
|
||||
return false;
|
||||
|
||||
var normalizedValue = NormalizeIndexedWriteValue(writeValue);
|
||||
nextArray.SetValue(ConvertArrayElementValue(normalizedValue, elementType), index);
|
||||
updatedArray = nextArray;
|
||||
return true;
|
||||
}
|
||||
|
||||
private static object? NormalizeIndexedWriteValue(object? value)
|
||||
{
|
||||
if (value is Array array && array.Length == 1)
|
||||
return array.GetValue(0);
|
||||
return value;
|
||||
}
|
||||
|
||||
private static object? ConvertArrayElementValue(object? value, Type elementType)
|
||||
{
|
||||
if (value == null)
|
||||
{
|
||||
if (elementType.IsValueType)
|
||||
return Activator.CreateInstance(elementType);
|
||||
return null;
|
||||
}
|
||||
|
||||
if (elementType.IsInstanceOfType(value))
|
||||
return value;
|
||||
|
||||
if (elementType == typeof(string))
|
||||
return value.ToString();
|
||||
|
||||
return Convert.ChangeType(value, elementType);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
#region Subscription Delivery
|
||||
|
||||
Reference in New Issue
Block a user