public void Check_Initial_Data() { // Arrange var targetValue = TargetValue; var targetData = DataConverter.ToBytes(targetValue, UInt16PlcItem.Endianness); // Act var item = new UInt16PlcItem(0, 0, targetValue); // Assert: Number → Data Assert.That(item.Value, Is.EqualTo(targetValue)); Assert.That((byte[])((IPlcItem)item).Value, Is.EqualTo(targetData)); }
public void Check_FromData() { // Arrange var targetValue = TargetValue; var targetData = DataConverter.ToBytes(targetValue, UInt16PlcItem.Endianness); var item = new UInt16PlcItem(0, 0); // Act: Data → Number ((IPlcItem)item).Value.TransferValuesFrom(targetData); // Assert Assert.That(item.Value, Is.EqualTo(targetValue)); Assert.That((byte[])((IPlcItem)item).Value, Is.EqualTo(targetData)); }
public void Check_If_Factor_Is_Applied_When_Writing(byte[] value) { // Arrange var factor = (byte)2; var targetLength = value.Length / factor; var numericItem = new UInt16PlcItem(0, 0); Func <string, IPlcItem <byte[]> > flexiblePlcItemFactory = name => new BytesPlcItem(0, 1, true, new byte[0], name); var dynamicPlcItem = new DynamicPlcItem <byte[]>(numericItem, flexiblePlcItemFactory, factor, null); // Act dynamicPlcItem.FlexiblePlcItem.Value = value; // Assert Assert.That(numericItem.Value, Is.EqualTo(targetLength)); Assert.That(dynamicPlcItem.FlexiblePlcItem.Value, Has.Length.EqualTo(value.Length)); }
public void Check_Clone() { // Arrange var item = new UInt16PlcItem(0, 0, TargetValue); // Act var clone = item.Clone(); // Check if both items are different references. Assert.False(Object.ReferenceEquals(item, clone)); // Check equality (Equals is overriden). Assert.AreEqual(item, clone); // Check the value. Assert.AreEqual(item.Value, clone.Value); }
public async Task MonitorDifferentIdenticalItems() { var firstMonitoredItem = new BytesPlcItem(dataBlock: Data.Datablock, position: Data.StartOfFixedBytes, byteAmount: 2); var secondMonitoredItem = new UInt16PlcItem(dataBlock: Data.Datablock, position: Data.StartOfFixedBytes); var thirdMonitoredItem = new BitsPlcItem(dataBlock: Data.Datablock, position: Data.StartOfFixedBytes, bitPosition: BitPosition.X0, bitAmount: 16); var differentReadItems = new HashSet <IPlcItem>(new ReferenceComparer()); var mockPlc = new MockPlc(); Func <ICollection <IPlcItem>, CancellationToken, Task> performReadItemsAsyncMock = (plcItems, cancellationToken) => { foreach (var plcItem in plcItems) { differentReadItems.Add(plcItem); } return(mockPlc.ReadItemsAsync(plcItems, cancellationToken)); }; // Create a mock of MockPlc that signals which items are read. var plcMock = new Mock <IPlc>(behavior: MockBehavior.Strict) { CallBase = true, }; plcMock .Setup(x => x.ReadItemsAsync(It.IsAny <IPlcItem[]>(), It.IsAny <CancellationToken>())) .Returns(performReadItemsAsyncMock) .Verifiable() ; // Create the monitor with the mocked instance. var monitoredPlc = new PollingMonitorablePlc(plcMock.Object); // Start monitoring those items. monitoredPlc.MonitorItem(firstMonitoredItem); monitoredPlc.MonitorItem(secondMonitoredItem); monitoredPlc.MonitorItem(thirdMonitoredItem); monitoredPlc.Start(); await Task.Delay(1000); monitoredPlc.Stop(); Assert.AreEqual(1, differentReadItems.Count); }
public DynamicUtf8PlcItem BuildDynamic() { this.Validate(); // ReSharper disable PossibleInvalidOperationException //! The validation method takes care of no value being null. INumericPlcItem numericPlcItem; if (_numericPlcItemType == typeof(BytePlcItem)) { numericPlcItem = new BytePlcItem(base.DataBlock.Value, base.Position.Value, initialValue: (byte)base.ByteAmount); } else if (_numericPlcItemType == typeof(UInt16PlcItem)) { numericPlcItem = new UInt16PlcItem(base.DataBlock.Value, base.Position.Value, initialValue: (UInt16)base.ByteAmount); } else if (_numericPlcItemType == typeof(UInt32PlcItem)) { numericPlcItem = new UInt32PlcItem(base.DataBlock.Value, base.Position.Value, initialValue: (UInt32)base.ByteAmount); } else if (_numericPlcItemType == typeof(WordPlcItem)) { numericPlcItem = new WordPlcItem(base.DataBlock.Value, base.Position.Value, initialValue: (UInt16)base.ByteAmount); } else if (_numericPlcItemType == typeof(DWordPlcItem)) { numericPlcItem = new DWordPlcItem(base.DataBlock.Value, base.Position.Value, initialValue: (UInt32)base.ByteAmount); } else { throw new NotSupportedException($"The numeric part of any dynamic plc item must be an {nameof(INumericPlcItem)}. Currently supported are the following concrete items: {nameof(BytePlcItem)}, {nameof(UInt16PlcItem)}, {nameof(UInt32PlcItem)}, {nameof(WordPlcItem)}, {nameof(DWordPlcItem)}"); } return(new DynamicUtf8PlcItem(numericPlcItem, _lengthFactor, _lengthLimit, base.InitialValue, base.Identifier)); // ReSharper restore PossibleInvalidOperationException }
[TestCase(DataConverter.Endianness.BigEndian, (ushort)50, (ushort)50)] // Value is smaller than limit → Value will be used. public void Check_If_Limit_Is_Respected_When_Reading(DataConverter.Endianness endianness, ushort value, ushort target) { // Arrange var limit = (uint)100; INumericPlcItem numericItem; if (endianness == DataConverter.Endianness.LittleEndian) { numericItem = new UInt16PlcItem(0, 0); } else { numericItem = new WordPlcItem(0, 0); } Func <string, IPlcItem <byte[]> > flexiblePlcItemFactory = name => new BytesPlcItem(0, 1, true, new byte[0], name); var dynamicPlcItem = new DynamicPlcItem <byte[]>(numericItem, flexiblePlcItemFactory, 1, limit); // Act numericItem.Value = value; // Assert Assert.That(numericItem.Value, Is.EqualTo(target)); Assert.That(dynamicPlcItem.FlexiblePlcItem.Value, Has.Length.EqualTo(target)); }
public void CheckItemBuilder() { var itemBuilder = new PlcItemBuilder(); var plcItem = itemBuilder .Construct("Generic") .ForData() .AtDatablock(0) .AtPosition(0, BitPosition.X2) .ForBitAmount(3) .Build() ; Assert.AreEqual((uint)3, plcItem.Value.Length); BitsPlcItem bitsItem = itemBuilder .ConstructBitsPlcItem() .ForFlags() .AtPosition(20, BitPosition.X5) .ForBitAmount(5) .Build() ; Assert.AreEqual((uint)5, ((IPlcItem)bitsItem).Value.Length); BitPlcItem bitItem = itemBuilder .ConstructBitPlcItem("Bit") .ForData() .AtDatablock(0) .AtPosition(5) .AsSet() .Build() ; Assert.AreEqual((uint)1, ((IPlcItem)bitItem).Value.Length); BytesPlcItem bytesItem = itemBuilder .ConstructBytesPlcItem(identifier: "Bytes") .ForOutput() .AtPosition(0) .WithInitialValue(new[] { byte.MinValue, byte.MaxValue }) .Build() ; Assert.AreEqual((uint)2, ((IPlcItem)bytesItem).Value.ByteLength); BytePlcItem byteItem = itemBuilder .ConstructBytePlcItem("Byte") .ForInput() .AtPosition(10) .WithInitialValue(Byte.MaxValue) .Build() ; Assert.AreEqual((uint)sizeof(Byte), ((IPlcItem)byteItem).Value.ByteLength); Int16PlcItem int16Item = itemBuilder .ConstructInt16PlcItem("Int16") .AtDatablock(0) .AtPosition(1) .WithoutInitialValue() .Build() ; Assert.AreEqual((uint)sizeof(Int16), ((IPlcItem)int16Item).Value.ByteLength); Int32PlcItem int32Item = itemBuilder .ConstructInt32PlcItem("Int32") .AtDatablock(0) .AtPosition(1) .WithInitialValue(int.MinValue) .Build() ; Assert.AreEqual((uint)sizeof(Int32), ((IPlcItem)int32Item).Value.ByteLength); Int64PlcItem int64Item = itemBuilder .ConstructInt64PlcItem("Int64") .AtDatablock(0) .AtPosition(1) .WithInitialValue(long.MinValue) .Build() ; Assert.AreEqual((uint)sizeof(Int64), ((IPlcItem)int64Item).Value.ByteLength); UInt16PlcItem uInt16Item = itemBuilder .ConstructUInt16PlcItem("UInt16") .AtDatablock(0) .AtPosition(1) .WithoutInitialValue() .Build() ; Assert.AreEqual((uint)sizeof(UInt16), ((IPlcItem)uInt16Item).Value.ByteLength); UInt32PlcItem uInt32PlcItem = itemBuilder .ConstructUInt32PlcItem("UInt32") .AtDatablock(0) .AtPosition(1) .WithInitialValue(uint.MaxValue) .Build() ; Assert.AreEqual((uint)sizeof(UInt32), ((IPlcItem)uInt32PlcItem).Value.ByteLength); UInt64PlcItem uInt64PlcItem = itemBuilder .ConstructUInt64PlcItem("UInt64") .AtDatablock(0) .AtPosition(1) .WithInitialValue(ulong.MaxValue) .Build() ; Assert.AreEqual((uint)sizeof(UInt64), ((IPlcItem)uInt64PlcItem).Value.ByteLength); WordPlcItem wordItem = itemBuilder .ConstructWordPlcItem("Word") .AtDatablock(0) .AtPosition(2) .WithInitialValue(32458) .Build() ; Assert.AreEqual((uint)2, ((IPlcItem)wordItem).Value.ByteLength); DWordPlcItem dwordItem = itemBuilder .ConstructDWordPlcItem("DWord") .AtDatablock(0) .AtPosition(2) .WithInitialValue(uint.MaxValue) .Build() ; Assert.AreEqual((uint)4, ((IPlcItem)dwordItem).Value.ByteLength); LWordPlcItem lwordItem = itemBuilder .ConstructLWordPlcItem("LWord") .AtDatablock(0) .AtPosition(2) .WithInitialValue(ulong.MaxValue) .Build() ; Assert.AreEqual((uint)8, ((IPlcItem)lwordItem).Value.ByteLength); TextPlcItem textItem = itemBuilder .ConstructTextPlcItem("Text") .WithEncoding(Encoding.UTF7) .AtDatablock(0) .AtPosition(3) .WithInitialValue("Some String") .Build() ; Assert.AreEqual((uint)Encoding.UTF7.GetBytes("Some String").Length, ((IPlcItem)textItem).Value.ByteLength); Utf8PlcItem utf8Item = itemBuilder .ConstructUtf8PlcItem("UTF-8") .AtDatablock(0) .AtPosition(4) .WithLength(10) .Build() ; Assert.AreEqual((uint)10, ((IPlcItem)utf8Item).Value.ByteLength); var initialText = "String whose length fits into a single byte."; DynamicUtf8PlcItem secondDynamicUtf8Item = itemBuilder .ConstructUtf8PlcItem("UTF-8") .AtDatablock(0) .AtPosition(4) .WithDynamicItemFromInitialValue(initialText) .BuildDynamic() ; Assert.That(secondDynamicUtf8Item.LengthPlcItem.Value, Is.EqualTo((uint)Encoding.UTF8.GetBytes(initialText).Length)); Assert.AreEqual(initialText, secondDynamicUtf8Item.Value); var items = new [] { plcItem, bitsItem, bitItem, bytesItem, byteItem, int16Item, int32Item, int64Item, uInt16Item, uInt32PlcItem, uInt64PlcItem, wordItem, dwordItem, lwordItem, textItem, utf8Item, secondDynamicUtf8Item, }; foreach (var item in items) { Debug.WriteLine($" -> {item}"); } }