diff --git a/.gitignore b/.gitignore index 809f06a76..ed8c08844 100644 --- a/.gitignore +++ b/.gitignore @@ -58,3 +58,5 @@ $tf/pendingchanges.tfb $tf/properties.tf1 project.lock.json **/.vs/ + +.claude/ \ No newline at end of file diff --git a/Sources/.editorconfig b/Sources/.editorconfig index 1bae2e959..116ea2776 100644 --- a/Sources/.editorconfig +++ b/Sources/.editorconfig @@ -50,4 +50,14 @@ csharp_new_line_before_catch = true csharp_new_line_before_finally = true csharp_indent_case_contents = true csharp_indent_switch_labels = true -csharp_preserve_single_line_statements = false \ No newline at end of file +csharp_preserve_single_line_statements = false +[*.cs] + +# Default severity for analyzer diagnostics with category 'StyleCop.CSharp.NamingRules' +dotnet_analyzer_diagnostic.category-StyleCop.CSharp.NamingRules.severity = none + +# Default severity for all analyzer diagnostics +dotnet_analyzer_diagnostic.severity = none + +# SA1314: Type parameter names should begin with T +dotnet_diagnostic.SA1314.severity = none diff --git a/Sources/Core/Directory.Build.props b/Sources/Core/Directory.Build.props index 15f391280..fa8e33c0e 100644 --- a/Sources/Core/Directory.Build.props +++ b/Sources/Core/Directory.Build.props @@ -3,15 +3,5 @@ - - - all - runtime; build; native; contentfiles; analyzers - - - - - $(EnlistmentRoot)\Sources\Microsoft.StreamProcessing.ruleset - diff --git a/Sources/Core/Microsoft.StreamProcessing.Provider/Microsoft.StreamProcessing.Provider.csproj b/Sources/Core/Microsoft.StreamProcessing.Provider/Microsoft.StreamProcessing.Provider.csproj index 1d9de4e69..00948d43b 100644 --- a/Sources/Core/Microsoft.StreamProcessing.Provider/Microsoft.StreamProcessing.Provider.csproj +++ b/Sources/Core/Microsoft.StreamProcessing.Provider/Microsoft.StreamProcessing.Provider.csproj @@ -1,7 +1,7 @@  - netstandard2.0 + net10.0 x64;AnyCPU @@ -11,19 +11,7 @@ - - - - - - - - - - - - - + diff --git a/Sources/Core/Microsoft.StreamProcessing/Aggregates/CountAggregate.cs b/Sources/Core/Microsoft.StreamProcessing/Aggregates/CountAggregate.cs index db3e0ab86..d4ab16d42 100644 --- a/Sources/Core/Microsoft.StreamProcessing/Aggregates/CountAggregate.cs +++ b/Sources/Core/Microsoft.StreamProcessing/Aggregates/CountAggregate.cs @@ -21,7 +21,7 @@ internal sealed class CountAggregate : ISummableAggregate> diff = (leftCount, rightCount) => leftCount - rightCount; public Expression> Difference() => diff; - private static readonly Expression> sum = (leftCount, rightCount) => leftCount - rightCount; + private static readonly Expression> sum = (leftCount, rightCount) => leftCount + rightCount; public Expression> Sum() => sum; private static readonly Expression> res = count => count; diff --git a/Sources/Core/Microsoft.StreamProcessing/Collections/SafeConcurrentDictionary.cs b/Sources/Core/Microsoft.StreamProcessing/Collections/SafeConcurrentDictionary.cs index 9b04f7206..153890de3 100644 --- a/Sources/Core/Microsoft.StreamProcessing/Collections/SafeConcurrentDictionary.cs +++ b/Sources/Core/Microsoft.StreamProcessing/Collections/SafeConcurrentDictionary.cs @@ -44,6 +44,18 @@ public TValue GetOrAdd(CacheKey key, Func valueFactory) [MethodImpl(MethodImplOptions.AggressiveInlining)] public IEnumerator> GetEnumerator() => this.dictionary.GetEnumerator(); + /// + /// Clears all entries from the dictionary and the per-key lock table. + /// Marked internal (not private) so that test code can clear the codegen cache + /// (e.g. EquiJoinStreamable.cachedPipes) to ensure deterministic test behavior + /// without relying on reflection. + /// + internal void Clear() + { + this.dictionary.Clear(); + this.keyLocks.Clear(); + } + IEnumerator IEnumerable.GetEnumerator() => GetEnumerator(); /// diff --git a/Sources/Core/Microsoft.StreamProcessing/Microsoft.StreamProcessing.csproj b/Sources/Core/Microsoft.StreamProcessing/Microsoft.StreamProcessing.csproj index b96b07891..967913da3 100644 --- a/Sources/Core/Microsoft.StreamProcessing/Microsoft.StreamProcessing.csproj +++ b/Sources/Core/Microsoft.StreamProcessing/Microsoft.StreamProcessing.csproj @@ -1,7 +1,7 @@  - netstandard2.0 + net10.0 x64;AnyCPU @@ -11,14 +11,7 @@ - - - - - - - - + diff --git a/Sources/Core/Microsoft.StreamProcessing/Operators/EquiJoin/EquiJoinStreamable.cs b/Sources/Core/Microsoft.StreamProcessing/Operators/EquiJoin/EquiJoinStreamable.cs index 4624db258..9c049504f 100644 --- a/Sources/Core/Microsoft.StreamProcessing/Operators/EquiJoin/EquiJoinStreamable.cs +++ b/Sources/Core/Microsoft.StreamProcessing/Operators/EquiJoin/EquiJoinStreamable.cs @@ -11,8 +11,10 @@ namespace Microsoft.StreamProcessing { internal sealed class EquiJoinStreamable : BinaryStreamable { - private static readonly SafeConcurrentDictionary> cachedPipes - = new SafeConcurrentDictionary>(); + // Internal (not private) so test code can call cachedPipes.Clear() to ensure + // deterministic behavior in tests that depend on a fresh codegen compile. + internal static readonly SafeConcurrentDictionary> cachedPipes + = new SafeConcurrentDictionary>(); private readonly JoinKind joinKind; private readonly Func> columnarGenerator; diff --git a/Sources/Core/Microsoft.StreamProcessing/Pipes/BinaryPipe.cs b/Sources/Core/Microsoft.StreamProcessing/Pipes/BinaryPipe.cs index 2c5ef1f0e..3b14ca8a8 100644 --- a/Sources/Core/Microsoft.StreamProcessing/Pipes/BinaryPipe.cs +++ b/Sources/Core/Microsoft.StreamProcessing/Pipes/BinaryPipe.cs @@ -183,6 +183,9 @@ public override void OnCompleted() Monitor.Enter(this.sync); try { + // Process any batches that were enqueued while another thread held the lock above. + // Monitor is reentrant, so ProcessPendingBatches()'s TryEnter will succeed here. + ProcessPendingBatches(); base.OnCompleted(); while (this.leftQueue.TryDequeue(out var leftBatch)) diff --git a/Sources/Core/Microsoft.StreamProcessing/Serializer/Encoders/BinaryDecoder.cs b/Sources/Core/Microsoft.StreamProcessing/Serializer/Encoders/BinaryDecoder.cs index 8392f8475..35880a25c 100644 --- a/Sources/Core/Microsoft.StreamProcessing/Serializer/Encoders/BinaryDecoder.cs +++ b/Sources/Core/Microsoft.StreamProcessing/Serializer/Encoders/BinaryDecoder.cs @@ -3,6 +3,7 @@ // Licensed under the MIT License // ********************************************************************* using System; +using System.Buffers; using System.IO; using System.Runtime.Serialization; using System.Text; @@ -110,18 +111,15 @@ public ulong DecodeULong() public float DecodeFloat() { - var value = new byte[4]; + Span value = stackalloc byte[4]; ReadAllRequiredBytes(value); - if (!BitConverter.IsLittleEndian) - { - Array.Reverse(value); - } - return BitConverter.ToSingle(value, 0); + if (!BitConverter.IsLittleEndian) value.Reverse(); + return BitConverter.ToSingle(value); } public double DecodeDouble() { - var value = new byte[8]; + Span value = stackalloc byte[8]; ReadAllRequiredBytes(value); long longValue = value[0] | (long)value[1] << 0x8 @@ -142,7 +140,21 @@ public byte[] DecodeByteArray() return array; } - public string DecodeString() => Encoding.UTF8.GetString(DecodeByteArray()); + public string DecodeString() + { + int byteCount = DecodeInt(); + if (byteCount == 0) return string.Empty; + var rented = ArrayPool.Shared.Rent(byteCount); + try + { + ReadAllRequiredBytes(rented.AsSpan(0, byteCount)); + return Encoding.UTF8.GetString(rented, 0, byteCount); + } + finally + { + ArrayPool.Shared.Return(rented); + } + } public int DecodeArrayChunk() { @@ -157,9 +169,9 @@ public int DecodeArrayChunk() public Guid DecodeGuid() { - var array = new byte[16]; - ReadAllRequiredBytes(array); - return new Guid(array); + Span value = stackalloc byte[16]; + ReadAllRequiredBytes(value); + return new Guid(value); } private void ReadAllRequiredBytes(byte[] array) @@ -172,15 +184,26 @@ private void ReadAllRequiredBytes(byte[] array) } } + private void ReadAllRequiredBytes(Span span) + { + int totalRead = 0; + while (totalRead < span.Length) + { + int read = this.stream.Read(span.Slice(totalRead)); + if (read == 0) + throw new SerializationException($"Unexpected end of stream: '{span.Length - totalRead}' bytes missing."); + totalRead += read; + } + } + private int ReadIntFixed() { - var value = new byte[4]; - this.stream.ReadAllRequiredBytes(value, 0, value.Length); - int intValue = value[0] + Span value = stackalloc byte[4]; + ReadAllRequiredBytes(value); + return value[0] | value[1] << 0x8 | value[2] << 0x10 | value[3] << 0x18; - return intValue; } public unsafe T[] DecodeArray() where T : struct diff --git a/Sources/Core/Microsoft.StreamProcessing/Serializer/Encoders/BinaryEncoder.cs b/Sources/Core/Microsoft.StreamProcessing/Serializer/Encoders/BinaryEncoder.cs index dd944275e..902c15699 100644 --- a/Sources/Core/Microsoft.StreamProcessing/Serializer/Encoders/BinaryEncoder.cs +++ b/Sources/Core/Microsoft.StreamProcessing/Serializer/Encoders/BinaryEncoder.cs @@ -3,6 +3,7 @@ // Licensed under the MIT License // ********************************************************************* using System; +using System.Buffers; using System.IO; using System.Text; using Microsoft.StreamProcessing.Internal; @@ -83,13 +84,10 @@ public void Encode(ulong value) public void Encode(float value) { - byte[] bytes = BitConverter.GetBytes(value); - if (!BitConverter.IsLittleEndian) - { - Array.Reverse(bytes); - } - - this.stream.Write(bytes, 0, bytes.Length); + Span bytes = stackalloc byte[4]; + BitConverter.TryWriteBytes(bytes, value); + if (!BitConverter.IsLittleEndian) bytes.Reverse(); + this.stream.Write(bytes); } public void Encode(double value) @@ -113,12 +111,40 @@ public void Encode(byte[] value) if (value.Length > 0) this.stream.Write(value, 0, value.Length); } + public void Encode(ReadOnlySpan span) + { + int count = span.Length; + Encode(count); + if (count > 0) + { + this.stream.Write(span); + } + } + public void Encode(string value) - => Encode(Encoding.UTF8.GetBytes(value ?? throw new ArgumentNullException(nameof(value)))); + { + if (value == null) throw new ArgumentNullException(nameof(value)); + int byteCount = Encoding.UTF8.GetByteCount(value); + var rented = ArrayPool.Shared.Rent(byteCount); + try + { + int written = Encoding.UTF8.GetBytes(value, rented); + Encode(rented.AsSpan(0, written)); + } + finally + { + ArrayPool.Shared.Return(rented); + } + } public void EncodeArrayChunk(int size) => Encode(size); - public void Encode(Guid value) => this.stream.Write(value.ToByteArray(), 0, 16); + public void Encode(Guid value) + { + Span bytes = stackalloc byte[16]; + value.TryWriteBytes(bytes); + this.stream.Write(bytes); + } private void WriteIntFixed(int encodedValue) { diff --git a/Sources/Core/Microsoft.StreamProcessing/Utilities/Config.cs b/Sources/Core/Microsoft.StreamProcessing/Utilities/Config.cs index badaa164f..1f7d1cf20 100644 --- a/Sources/Core/Microsoft.StreamProcessing/Utilities/Config.cs +++ b/Sources/Core/Microsoft.StreamProcessing/Utilities/Config.cs @@ -467,8 +467,12 @@ public static string Describe() // in VSTest, which is a good thing, since Config is static and those tests may clash otherwise. internal sealed class ConfigModifier { - // lockable gate allowing only one ConfigModifier active at a time - private static readonly object gate = new object(); + // Serializes concurrent ConfigModifier usage across tests. + // SemaphoreSlim instead of Monitor so that async tests can release from a different thread. + // AsyncLocal depth counter makes it re-entrant within the same async call context (e.g. nested + // using blocks within a single test) without blocking on the semaphore a second time. + private static readonly SemaphoreSlim gate = new SemaphoreSlim(1, 1); + private static readonly AsyncLocal gateDepth = new AsyncLocal(); // collection of Config modifications private readonly List modifications = new List(); @@ -723,7 +727,8 @@ public ConfigModifier SerializationCompressionLevel(SerializationCompressionLeve public IDisposable Modify() { - Monitor.Enter(gate); + if (gateDepth.Value == 0) gate.Wait(); + gateDepth.Value++; foreach (var m in this.modifications) m.Modify(); @@ -732,7 +737,8 @@ public IDisposable Modify() foreach (var m in this.modifications) m.Modify(); - Monitor.Exit(gate); + gateDepth.Value--; + if (gateDepth.Value == 0) gate.Release(); }); } diff --git a/Sources/Core/Microsoft.StreamProcessing/Utilities/Native32.cs b/Sources/Core/Microsoft.StreamProcessing/Utilities/Native32.cs index f2924c0e7..d19a7ca57 100644 --- a/Sources/Core/Microsoft.StreamProcessing/Utilities/Native32.cs +++ b/Sources/Core/Microsoft.StreamProcessing/Utilities/Native32.cs @@ -74,8 +74,16 @@ internal static void AffinitizeThread(int processor) { if (utid == pt.Id) { - long AffinityMask = 1 << processor; - pt.ProcessorAffinity = (IntPtr)(AffinityMask); // Set affinity for this + if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) + { + pt.IdealProcessor = processor; + } + + if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows)) + { + long AffinityMask = 1 << processor; + pt.ProcessorAffinity = (IntPtr)(AffinityMask); // Set affinity for this + } } } } diff --git a/Sources/Test/Directory.Build.props b/Sources/Test/Directory.Build.props index 588c632b2..a3b945e01 100644 --- a/Sources/Test/Directory.Build.props +++ b/Sources/Test/Directory.Build.props @@ -28,7 +28,7 @@ - + diff --git a/Sources/Test/Microsoft.StreamProcessing.Test.ruleset b/Sources/Test/Microsoft.StreamProcessing.Test.ruleset index ca4f78706..c656edfee 100644 --- a/Sources/Test/Microsoft.StreamProcessing.Test.ruleset +++ b/Sources/Test/Microsoft.StreamProcessing.Test.ruleset @@ -4,6 +4,6 @@ - + \ No newline at end of file diff --git a/Sources/Test/SimpleTesting/AdHocTests.cs b/Sources/Test/SimpleTesting/AdHocTests.cs index 41c0cca20..f201a7204 100644 --- a/Sources/Test/SimpleTesting/AdHocTests.cs +++ b/Sources/Test/SimpleTesting/AdHocTests.cs @@ -44,7 +44,7 @@ public void Properties() .ToObservable() .ToStreamable(DisorderPolicy.Throw(), FlushPolicy.FlushOnPunctuation, PeriodicPunctuationPolicy.None(), OnCompletedPolicy.None); - var q2 = q1.Select(x => string.Join(",", x.A, x.B, x.C, x.D, x.E)); + var q2 = q1.Select(x => string.Join(",", new object[] { x.A, x.B, x.C, x.D, x.E })); int count = 0; q2.ToStreamEventObservable().ForEachAsync(x => count++).Wait(); @@ -67,7 +67,7 @@ public void Fields() .ToObservable() .ToStreamable(DisorderPolicy.Throw(), FlushPolicy.FlushOnPunctuation, PeriodicPunctuationPolicy.None(), OnCompletedPolicy.None); - var q2 = q1.Select(x => string.Join(",", x.A, x.B, x.C, x.D, x.E)); + var q2 = q1.Select(x => string.Join(",", new object[] { x.A, x.B, x.C, x.D, x.E })); int count = 0; q2.ToStreamEventObservable().ForEachAsync(x => count++).Wait(); @@ -141,11 +141,11 @@ private void TestSerialization() ms.Position = 0; ColumnBatch resultStr = s.Deserialize(ms); - Assert.IsTrue(resultStr.UsedLength == inputStr.UsedLength); + Assert.AreEqual(inputStr.UsedLength, resultStr.UsedLength); for (int j = 0; j < inputStr.UsedLength; j++) { - Assert.IsTrue(inputStr.col[j] == resultStr.col[j]); + Assert.AreEqual(resultStr.col[j], inputStr.col[j]); } resultStr.ReturnClear(); inputStr.ReturnClear(); @@ -165,9 +165,9 @@ public void StreamEventArrayIngress1() var s = input.ToObservable(); var str = s.ToStreamable(); var output = str.ToStreamMessageObservable().ToEnumerable().ToArray(); - Assert.IsTrue(output.Length == 1); // first batch with all data and one punctuation - Assert.IsTrue(output[0].Count == length + 1); - Assert.IsTrue(output[0].vother.col[output[0].Count - 1] == StreamEvent.PunctuationOtherTime); + Assert.HasCount(1, output); // first batch with all data and one punctuation + Assert.AreEqual(length + 1, output[0].Count); + Assert.AreEqual(StreamEvent.PunctuationOtherTime, output[0].vother.col[output[0].Count - 1]); for (int i = 0; i < output.Length; i++) output[i].Free(); } @@ -185,11 +185,11 @@ public void StreamEventArrayIngress2() var s = input.ToObservable(); var str = s.ToStreamable(); var output = str.ToStreamMessageObservable().ToEnumerable().ToArray(); - Assert.IsTrue(output.Length == 4); // four data batches - Assert.IsTrue(output[0].Count + output[1].Count + output[2].Count + output[3].Count == length + 1); + Assert.HasCount(4, output); // four data batches + Assert.AreEqual(length + 1, output[0].Count + output[1].Count + output[2].Count + output[3].Count); // fourth data batch should have a punctuation at the end - Assert.IsTrue(output[3].vother.col[output[3].Count - 1] == StreamEvent.PunctuationOtherTime); + Assert.AreEqual(StreamEvent.PunctuationOtherTime, output[3].vother.col[output[3].Count - 1]); for (int i = 0; i < output.Length; i++) output[i].Free(); } @@ -211,15 +211,15 @@ public void StreamEventArrayIngress3() // 10 pairs of data and punc, then one with just a punctuation at infinity int expectedDataBatches = 11; - Assert.IsTrue(output.Length == expectedDataBatches); + Assert.HasCount(expectedDataBatches, output); var dataEventCount = 0; for (int i = 0; i < output.Length; i++) { // Data batch should end with a punctuation - Assert.IsTrue(output[i].vother.col[output[i].Count - 1] == StreamEvent.PunctuationOtherTime); + Assert.AreEqual(StreamEvent.PunctuationOtherTime, output[i].vother.col[output[i].Count - 1]); dataEventCount += output[i].Count - 1; // exclude punctuation } - Assert.IsTrue(dataEventCount == length - 10); // because every 10th row was a punctuation, not a data row + Assert.AreEqual(length - 10, dataEventCount); // because every 10th row was a punctuation, not a data row for (int i = 0; i < output.Length; i++) output[i].Free(); } @@ -255,7 +255,7 @@ public void PartitionedStreamAdjustIngressPolicy() egress.Wait(); output = output.Where(o => o.IsData).ToList(); - Assert.AreEqual(2, output.Count); + Assert.HasCount(2, output); Assert.AreEqual(70, output[0].SyncTime); Assert.AreEqual(22, output[1].SyncTime); } @@ -920,11 +920,11 @@ public void SinglePunctuationBatchTimestamps() batch => { var min = batch.MinTimestamp; - Assert.IsTrue(min >= currentMin); + Assert.IsGreaterThanOrEqualTo(currentMin, min); currentMin = min; var max = batch.MaxTimestamp; - Assert.IsTrue(max >= currentMax); + Assert.IsGreaterThanOrEqualTo(currentMax, max); currentMax = max; batch.Free(); @@ -1311,8 +1311,10 @@ public async Task DisposeTest1() await inputTask; // Make sure we really got an output data event. - Assert.IsTrue(lastSeenSubscription > 0); + Assert.IsGreaterThan(0, lastSeenSubscription); } + + public TestContext TestContext { get; set; } } [TestClass] @@ -1412,7 +1414,7 @@ public struct NormalizedHttpEvent countedNE = countedNE.AlterEventDuration(1); var output2 = countedNE.ToStreamEventObservable(ReshapingPolicy.CoalesceEndEdges).ToEnumerable().ToArray(); - Assert.IsTrue(output2.Count() == 9); + Assert.AreEqual(9, output2.Count()); } } @@ -1871,7 +1873,7 @@ public void LeftJoinOutOfOrder() process.Flush(); var outputData = output.Where(o => o.IsData).ToList(); - Assert.IsTrue(outputData.Count == 2); + Assert.HasCount(2, outputData); } [TestMethod, TestCategory("Gated")] @@ -1949,7 +1951,7 @@ public void StartEdge1() .ToArray(); var x = events.Length; - Assert.IsTrue(x == inputEnumerable.Count()); + Assert.AreEqual(inputEnumerable.Count(), x); } } @@ -2133,12 +2135,14 @@ public void JoinClipTest() }); var result = successes.ToStreamEventObservable().ToEnumerable().ToArray(); - Assert.IsTrue(false); // should never reach here. + Assert.Fail(); // should never reach here. } - catch (Exception e) + catch (InvalidOperationException) { - Assert.IsTrue(e is InvalidOperationException); + // expected, because the Join should not be able to match the clipped events with the finishing events, since the clipped events have had their lifetime shifted by 1 tick, and thus should not overlap with the finishing events. + return; } + Assert.Fail(); // should never reach here. } /// @@ -2249,7 +2253,7 @@ public void Select8() .ToEnumerable() .ToArray() ; - Assert.IsTrue(expected.Count() == output.Length); + Assert.AreEqual(output.Length, expected.Count()); for (int i = 0; i < output.Length; i++) Assert.IsTrue(expected.ElementAt(i).Equals(output[i])); } @@ -2321,6 +2325,21 @@ public class LeftComparerPayload_WithCodegen : TestWithConfigSettingsAndMemoryLe public LeftComparerPayload_WithCodegen() : base(new ConfigModifier().DontFallBackToRowBasedExecution(true)) { } + // Named result type so the full closed generic EquiJoinStreamable<,,,,> can be + // referenced at compile time (anonymous types cannot be named in typeof/generic arguments). + public struct JoinResult { public int LeftX; public int RightX; } + + [TestInitialize] + public void ClearCodegenCache() + { + // Clear the EquiJoin codegen cache before each test so that JoinTestWithException + // always triggers a fresh compile and deterministically throws StreamProcessingException, + // regardless of which tests ran before it in the same process. + // The join is built via Map+Reduce, so the inner EquiJoinStreamable uses TKey=CompoundGroupKey. + EquiJoinStreamable, ClassOverridingEquals, int, JoinResult> + .cachedPipes.Clear(); + } + public class ClassOverridingEquals { public int x; @@ -2330,9 +2349,10 @@ public class ClassOverridingEquals } /// - /// This test has a left comparer which has a reference to the left - /// payload instead of just to its fields. This causes the streamable - /// to thrown an exception. + /// This test has a left comparer which has a reference to the left payload instead of + /// just to its fields. Codegen should always throw StreamProcessingException when + /// compiling this join fresh. The [TestInitialize] method clears the codegen cache + /// before this test runs to ensure deterministic behavior in the full test suite. /// [TestMethod] public void JoinTestWithException() @@ -2349,20 +2369,17 @@ public void JoinTestWithException() .ToStreamable() ; - bool exceptionHappened = false; + bool threw = false; try { - var result = stream1 - .Join(stream2, e => e.x, e => e, (left, right) => new { LeftX = left.x, RightX = right, }) - .ToStreamEventObservable() - .ToEnumerable() - .ToArray(); - } - catch (StreamProcessingException) - { - exceptionHappened = true; + stream1 + .Join(stream2, e => e.x, e => e, (left, right) => new JoinResult { LeftX = left.x, RightX = right }) + .ToStreamEventObservable() + .ToEnumerable() + .ToArray(); } - Assert.IsTrue(exceptionHappened); + catch (StreamProcessingException) { threw = true; } + Assert.IsTrue(threw, "Expected StreamProcessingException from codegen failure on ClassOverridingEquals"); } } @@ -2404,18 +2421,15 @@ public void JoinTestWithoutException() .ToStreamable() ; - try - { - var result = stream1 + + var result = stream1 .Join(stream2, e => e.x, e => e, (left, right) => new { LeftX = left.x, RightX = right, }) .ToStreamEventObservable() .ToEnumerable() .ToArray(); - Assert.IsTrue(true); // just test that no exception happened - } - catch (Exception) + if (object.ReferenceEquals(result, null)) { - Assert.IsTrue(false); // should never reach here. + // just to use the result and avoid "unused variable" warning } } diff --git a/Sources/Test/SimpleTesting/CheckpointRestoreTests.cs b/Sources/Test/SimpleTesting/CheckpointRestoreTests.cs index 02483aca7..1a0d6a350 100644 --- a/Sources/Test/SimpleTesting/CheckpointRestoreTests.cs +++ b/Sources/Test/SimpleTesting/CheckpointRestoreTests.cs @@ -1318,7 +1318,7 @@ public void BasicDisorderAdjustPolicyRow() postCheckpointSubject.OnCompleted(); outputAsync2.Wait(); - Assert.IsTrue(outputList.Count == 10000); + Assert.HasCount(10000, outputList); preCheckpointSubject.OnCompleted(); } @@ -2790,7 +2790,7 @@ public void BasicDisorderAdjustPolicyRowSmallBatch() postCheckpointSubject.OnCompleted(); outputAsync2.Wait(); - Assert.IsTrue(outputList.Count == 10000); + Assert.HasCount(10000, outputList); preCheckpointSubject.OnCompleted(); } @@ -4260,7 +4260,7 @@ public void BasicDisorderAdjustPolicyColumnar() postCheckpointSubject.OnCompleted(); outputAsync2.Wait(); - Assert.IsTrue(outputList.Count == 10000); + Assert.HasCount(10000, outputList); preCheckpointSubject.OnCompleted(); } @@ -5732,7 +5732,7 @@ public void BasicDisorderAdjustPolicyColumnarSmallBatch() postCheckpointSubject.OnCompleted(); outputAsync2.Wait(); - Assert.IsTrue(outputList.Count == 10000); + Assert.HasCount(10000, outputList); preCheckpointSubject.OnCompleted(); } diff --git a/Sources/Test/SimpleTesting/Collections/AbstractEventBatch.cs b/Sources/Test/SimpleTesting/Collections/AbstractEventBatch.cs index 28e73fb35..c07b95977 100644 --- a/Sources/Test/SimpleTesting/Collections/AbstractEventBatch.cs +++ b/Sources/Test/SimpleTesting/Collections/AbstractEventBatch.cs @@ -43,21 +43,21 @@ public void ComputeMinMax_Basic() // (a) message.Count = 0; - Assert.IsTrue(message.MinTimestamp == StreamEvent.MinSyncTime, "Empty message with Count=0 has MinTimestamp <> 0."); - Assert.IsTrue(message.MaxTimestamp == StreamEvent.MaxSyncTime, "Empty message with Count=0 has MaxTimestamp <> inf-1."); + Assert.AreEqual(StreamEvent.MinSyncTime, message.MinTimestamp, "Empty message with Count=0 has MinTimestamp <> 0."); + Assert.AreEqual(StreamEvent.MaxSyncTime, message.MaxTimestamp, "Empty message with Count=0 has MaxTimestamp <> inf-1."); // (b) message.Count = 1; message.vsync.col[0] = TESTVALUE; - Assert.IsTrue(message.MinTimestamp == StreamEvent.MinSyncTime, "Empty message with Count=1 has MinTimestamp <> 0."); - Assert.IsTrue(message.MaxTimestamp == StreamEvent.MaxSyncTime, "Empty message with Count=1 has MaxTimestamp <> inf-1."); + Assert.AreEqual(StreamEvent.MinSyncTime, message.MinTimestamp, "Empty message with Count=1 has MinTimestamp <> 0."); + Assert.AreEqual(StreamEvent.MaxSyncTime, message.MaxTimestamp, "Empty message with Count=1 has MaxTimestamp <> inf-1."); // (c) message.Count = 1; message.vsync.col[0] = TESTVALUE; OccupyAt(message, 0); - Assert.IsTrue(message.MinTimestamp == TESTVALUE, "Empty message with Count=1 has MinTimestamp <> TESTVALUE."); - Assert.IsTrue(message.MaxTimestamp == TESTVALUE, "Empty message with Count=1 has MaxTimestamp <> TESTVALUE"); + Assert.AreEqual(TESTVALUE, message.MinTimestamp, "Empty message with Count=1 has MinTimestamp <> TESTVALUE."); + Assert.AreEqual(TESTVALUE, message.MaxTimestamp, "Empty message with Count=1 has MaxTimestamp <> TESTVALUE"); VacateAt(message, 0); message.vsync.col[0] = 0; @@ -65,14 +65,14 @@ public void ComputeMinMax_Basic() message.Count = 100; message.vsync.col[5] = TESTVALUE - 1; message.vsync.col[42] = TESTVALUE; - Assert.IsTrue(message.MinTimestamp == StreamEvent.MinSyncTime, "Empty message with Count>1 has MinTimestamp <> 0."); - Assert.IsTrue(message.MaxTimestamp == StreamEvent.MaxSyncTime, "Empty message with Count>1 has MaxTimestamp <> inf-1"); + Assert.AreEqual(StreamEvent.MinSyncTime, message.MinTimestamp, "Empty message with Count>1 has MinTimestamp <> 0."); + Assert.AreEqual(StreamEvent.MaxSyncTime, message.MaxTimestamp, "Empty message with Count>1 has MaxTimestamp <> inf-1"); // (e) OccupyAt(message, 5); OccupyAt(message, 42); - Assert.IsTrue(message.MinTimestamp == TESTVALUE - 1, "Non-empty message with Count>1 has MinTimestamp <> TESTVALUE-1."); - Assert.IsTrue(message.MaxTimestamp == TESTVALUE, "Non-empty message with Count>1 has MaxTimestamp <> TESTVALUE"); + Assert.AreEqual(TESTVALUE - 1, message.MinTimestamp, "Non-empty message with Count>1 has MinTimestamp <> TESTVALUE-1."); + Assert.AreEqual(TESTVALUE, message.MaxTimestamp, "Non-empty message with Count>1 has MaxTimestamp <> TESTVALUE"); VacateAt(message, 5); VacateAt(message, 42); message.vsync.col[5] = 0; @@ -161,21 +161,21 @@ public void ComputeMinMax_Partitioned_Basic() // (a) message.Count = 0; - Assert.IsTrue(message.MinTimestamp == StreamEvent.MinSyncTime, "Empty message with Count=0 has MinTimestamp <> 0."); - Assert.IsTrue(message.MaxTimestamp == StreamEvent.MaxSyncTime, "Empty message with Count=0 has MaxTimestamp <> inf-1."); + Assert.AreEqual(StreamEvent.MinSyncTime, message.MinTimestamp, "Empty message with Count=0 has MinTimestamp <> 0."); + Assert.AreEqual(StreamEvent.MaxSyncTime, message.MaxTimestamp, "Empty message with Count=0 has MaxTimestamp <> inf-1."); // (b) message.Count = 1; message.vsync.col[0] = TESTVALUE; - Assert.IsTrue(message.MinTimestamp == StreamEvent.MinSyncTime, "Empty message with Count=1 has MinTimestamp <> 0."); - Assert.IsTrue(message.MaxTimestamp == StreamEvent.MaxSyncTime, "Empty message with Count=1 has MaxTimestamp <> inf-1."); + Assert.AreEqual(StreamEvent.MinSyncTime, message.MinTimestamp, "Empty message with Count=1 has MinTimestamp <> 0."); + Assert.AreEqual(StreamEvent.MaxSyncTime, message.MaxTimestamp, "Empty message with Count=1 has MaxTimestamp <> inf-1."); // (c) message.Count = 1; message.vsync.col[0] = TESTVALUE; OccupyAt(message, 0); - Assert.IsTrue(message.MinTimestamp == TESTVALUE, "Empty message with Count=1 has MinTimestamp <> TESTVALUE."); - Assert.IsTrue(message.MaxTimestamp == TESTVALUE, "Empty message with Count=1 has MaxTimestamp <> TESTVALUE"); + Assert.AreEqual(TESTVALUE, message.MinTimestamp, "Empty message with Count=1 has MinTimestamp <> TESTVALUE."); + Assert.AreEqual(TESTVALUE, message.MaxTimestamp, "Empty message with Count=1 has MaxTimestamp <> TESTVALUE"); VacateAt(message, 0); message.vsync.col[0] = 0; @@ -183,14 +183,14 @@ public void ComputeMinMax_Partitioned_Basic() message.Count = 100; message.vsync.col[5] = TESTVALUE - 1; message.vsync.col[42] = TESTVALUE; - Assert.IsTrue(message.MinTimestamp == StreamEvent.MinSyncTime, "Empty message with Count>1 has MinTimestamp <> 0."); - Assert.IsTrue(message.MaxTimestamp == StreamEvent.MaxSyncTime, "Empty message with Count>1 has MaxTimestamp <> inf-1"); + Assert.AreEqual(StreamEvent.MinSyncTime, message.MinTimestamp, "Empty message with Count>1 has MinTimestamp <> 0."); + Assert.AreEqual(StreamEvent.MaxSyncTime, message.MaxTimestamp, "Empty message with Count>1 has MaxTimestamp <> inf-1"); // (e) OccupyAt(message, 5); OccupyAt(message, 42); - Assert.IsTrue(message.MinTimestamp == TESTVALUE - 1, "Non-empty message with Count>1 has MinTimestamp <> TESTVALUE-1."); - Assert.IsTrue(message.MaxTimestamp == TESTVALUE, "Non-empty message with Count>1 has MaxTimestamp <> TESTVALUE"); + Assert.AreEqual(TESTVALUE - 1, message.MinTimestamp, "Non-empty message with Count>1 has MinTimestamp <> TESTVALUE-1."); + Assert.AreEqual(TESTVALUE, message.MaxTimestamp, "Non-empty message with Count>1 has MaxTimestamp <> TESTVALUE"); VacateAt(message, 5); VacateAt(message, 42); message.vsync.col[5] = 0; @@ -218,14 +218,14 @@ public void ComputeMinMax_Partitioned_Compound_Basic() message.Count = 100; message.vsync.col[5] = TESTVALUE; message.vsync.col[42] = TESTVALUE - 1; - Assert.IsTrue(message.MinTimestamp == StreamEvent.MinSyncTime, "Empty message with Count>1 has MinTimestamp <> 0."); - Assert.IsTrue(message.MaxTimestamp == StreamEvent.MaxSyncTime, "Empty message with Count>1 has MaxTimestamp <> inf-1"); + Assert.AreEqual(StreamEvent.MinSyncTime, message.MinTimestamp, "Empty message with Count>1 has MinTimestamp <> 0."); + Assert.AreEqual(StreamEvent.MaxSyncTime, message.MaxTimestamp, "Empty message with Count>1 has MaxTimestamp <> inf-1"); // (e) OccupyAt(message, 5); OccupyAt(message, 42); - Assert.IsTrue(message.MinTimestamp == TESTVALUE - 1, "Non-empty message with Count>1 has MinTimestamp <> TESTVALUE-1."); - Assert.IsTrue(message.MaxTimestamp == TESTVALUE, "Non-empty message with Count>1 has MaxTimestamp <> TESTVALUE"); + Assert.AreEqual(TESTVALUE - 1, message.MinTimestamp, "Non-empty message with Count>1 has MinTimestamp <> TESTVALUE-1."); + Assert.AreEqual(TESTVALUE, message.MaxTimestamp, "Non-empty message with Count>1 has MaxTimestamp <> TESTVALUE"); VacateAt(message, 5); VacateAt(message, 42); message.vsync.col[5] = 0; diff --git a/Sources/Test/SimpleTesting/Collections/FastListTest.cs b/Sources/Test/SimpleTesting/Collections/FastListTest.cs index 946f4c7c9..11c1957e0 100644 --- a/Sources/Test/SimpleTesting/Collections/FastListTest.cs +++ b/Sources/Test/SimpleTesting/Collections/FastListTest.cs @@ -39,9 +39,9 @@ private static void SimpleListTest() int indexA2 = list.Insert("a"); int indexB2 = list.Insert("b"); - Assert.IsTrue(indexA != indexA2); - Assert.IsTrue(indexA != indexB); - Assert.IsTrue(indexA2 != indexB2); + Assert.AreNotEqual(indexA2, indexA); + Assert.AreNotEqual(indexB, indexA); + Assert.AreNotEqual(indexB2, indexA2); Assert.IsFalse(list.IsEmpty); Assert.AreEqual(4, list.Count); @@ -131,7 +131,7 @@ private static void BetterListTest() { check += list.Values[index]; } - Assert.IsTrue(sum == check); + Assert.AreEqual(check, sum); } } } diff --git a/Sources/Test/SimpleTesting/Collections/FastMapTest.cs b/Sources/Test/SimpleTesting/Collections/FastMapTest.cs index 13cfb25c2..51750f2bf 100644 --- a/Sources/Test/SimpleTesting/Collections/FastMapTest.cs +++ b/Sources/Test/SimpleTesting/Collections/FastMapTest.cs @@ -40,9 +40,9 @@ private static void SimpleMapTest() int indexA5Two = map.Insert(5, "a"); int indexB5 = map.Insert(5, "b"); - Assert.IsTrue(indexA5 != indexA5Two); - Assert.IsTrue(indexA5 != indexB5); - Assert.IsTrue(indexA5Two != indexB5); + Assert.AreNotEqual(indexA5Two, indexA5); + Assert.AreNotEqual(indexB5, indexA5); + Assert.AreNotEqual(indexB5, indexA5Two); Assert.IsFalse(map.IsEmpty); Assert.AreEqual(4, map.Count); diff --git a/Sources/Test/SimpleTesting/Common.cs b/Sources/Test/SimpleTesting/Common.cs index 29a080ad0..9ef0d7ca7 100644 --- a/Sources/Test/SimpleTesting/Common.cs +++ b/Sources/Test/SimpleTesting/Common.cs @@ -183,11 +183,6 @@ public static IEnumerable> ToEvents(this IEnumerable input, yield return StreamEvent.CreateInterval(vsSelector(e), veSelector(e), e); } } - -#if NET472 - // string.Split has different signatures across .NET Framework/Core, so use an extension so we can use a single signature - public static string[] Split(this string original, char separator, StringSplitOptions options) => original.Split(separator); -#endif } public static class Helpers diff --git a/Sources/Test/SimpleTesting/GlobalSuppressions.cs b/Sources/Test/SimpleTesting/GlobalSuppressions.cs new file mode 100644 index 000000000..c89b555bf --- /dev/null +++ b/Sources/Test/SimpleTesting/GlobalSuppressions.cs @@ -0,0 +1,24 @@ +// This file is used by Code Analysis to maintain SuppressMessage +// attributes that are applied to this project. +// Project-level suppressions either have no target or are given +// a specific target and scoped to a namespace, type, member, etc. + +using System.Diagnostics.CodeAnalysis; + +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsColumnar.CheckpointRegressionColumnar")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsColumnar.MaxBug0Columnar")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsColumnar.MaxBug1Columnar")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsColumnar.MaxBug2Columnar")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsColumnarSmallBatch.CheckpointRegressionColumnarSmallBatch")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsColumnarSmallBatch.MaxBug0ColumnarSmallBatch")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsColumnarSmallBatch.MaxBug1ColumnarSmallBatch")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsColumnarSmallBatch.MaxBug2ColumnarSmallBatch")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsRow.CheckpointRegressionRow")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsRow.MaxBug0Row")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsRow.MaxBug1Row")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsRow.MaxBug2Row")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsRowSmallBatch.CheckpointRegressionRowSmallBatch")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsRowSmallBatch.MaxBug0RowSmallBatch")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsRowSmallBatch.MaxBug1RowSmallBatch")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1300:Element should begin with upper-case letter", Justification = "", Scope = "member", Target = "~M:SimpleTesting.CheckpointRestoreTestsRowSmallBatch.MaxBug2RowSmallBatch")] +[assembly: SuppressMessage("StyleCop.CSharp.NamingRules", "SA1305:Field names should not use Hungarian notation", Justification = "", Scope = "member", Target = "~M:SimpleTesting.Extensions.ToEvents``1(System.Collections.Generic.IEnumerable{``0},System.Func{``0,System.Int64},System.Func{``0,System.Int64})~System.Collections.Generic.IEnumerable{Microsoft.StreamProcessing.StreamEvent{``0}}")] diff --git a/Sources/Test/SimpleTesting/IngressEgress/DisorderedIngressAndEgressTests.cs b/Sources/Test/SimpleTesting/IngressEgress/DisorderedIngressAndEgressTests.cs index a750c1dea..ea0c22f96 100644 --- a/Sources/Test/SimpleTesting/IngressEgress/DisorderedIngressAndEgressTests.cs +++ b/Sources/Test/SimpleTesting/IngressEgress/DisorderedIngressAndEgressTests.cs @@ -1186,7 +1186,7 @@ public void DisorderedStartEdgeTestRowThrow105() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -1229,7 +1229,7 @@ public void DisorderedIntervalTestRowThrow105() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -1285,7 +1285,7 @@ public void DisorderedStartEdgeTestRowThrow105Diagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -1332,7 +1332,7 @@ public void DisorderedIntervalTestRowThrow105Diagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -1616,7 +1616,7 @@ public void DisorderedStartEdgeTestRowThrow105Time() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -1659,7 +1659,7 @@ public void DisorderedIntervalTestRowThrow105Time() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -1715,7 +1715,7 @@ public void DisorderedStartEdgeTestRowThrow105TimeDiagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -1762,7 +1762,7 @@ public void DisorderedIntervalTestRowThrow105TimeDiagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -4463,7 +4463,7 @@ public void DisorderedStartEdgeTestRowSmallBatchThrow105() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -4506,7 +4506,7 @@ public void DisorderedIntervalTestRowSmallBatchThrow105() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -4563,7 +4563,7 @@ public void DisorderedStartEdgeTestRowSmallBatchThrow105Diagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -4610,7 +4610,7 @@ public void DisorderedIntervalTestRowSmallBatchThrow105Diagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -4897,7 +4897,7 @@ public void DisorderedStartEdgeTestRowSmallBatchThrow105Time() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -4940,7 +4940,7 @@ public void DisorderedIntervalTestRowSmallBatchThrow105Time() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -4997,7 +4997,7 @@ public void DisorderedStartEdgeTestRowSmallBatchThrow105TimeDiagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -5044,7 +5044,7 @@ public void DisorderedIntervalTestRowSmallBatchThrow105TimeDiagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -7746,7 +7746,7 @@ public void DisorderedStartEdgeTestColumnarThrow105() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -7789,7 +7789,7 @@ public void DisorderedIntervalTestColumnarThrow105() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -7845,7 +7845,7 @@ public void DisorderedStartEdgeTestColumnarThrow105Diagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -7892,7 +7892,7 @@ public void DisorderedIntervalTestColumnarThrow105Diagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -8176,7 +8176,7 @@ public void DisorderedStartEdgeTestColumnarThrow105Time() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -8219,7 +8219,7 @@ public void DisorderedIntervalTestColumnarThrow105Time() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -8275,7 +8275,7 @@ public void DisorderedStartEdgeTestColumnarThrow105TimeDiagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -8322,7 +8322,7 @@ public void DisorderedIntervalTestColumnarThrow105TimeDiagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -11023,7 +11023,7 @@ public void DisorderedStartEdgeTestColumnarSmallBatchThrow105() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -11066,7 +11066,7 @@ public void DisorderedIntervalTestColumnarSmallBatchThrow105() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -11123,7 +11123,7 @@ public void DisorderedStartEdgeTestColumnarSmallBatchThrow105Diagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -11170,7 +11170,7 @@ public void DisorderedIntervalTestColumnarSmallBatchThrow105Diagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -11457,7 +11457,7 @@ public void DisorderedStartEdgeTestColumnarSmallBatchThrow105Time() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -11500,7 +11500,7 @@ public void DisorderedIntervalTestColumnarSmallBatchThrow105Time() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } @@ -11557,7 +11557,7 @@ public void DisorderedStartEdgeTestColumnarSmallBatchThrow105TimeDiagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } @@ -11604,7 +11604,7 @@ public void DisorderedIntervalTestColumnarSmallBatchThrow105TimeDiagnostic() } catch(Exception) { - Assert.IsTrue(true); // Todo. Verify if the ingress/egress before the exception was correct. + // Todo. Verify if the ingress/egress before the exception was correct. } } } diff --git a/Sources/Test/SimpleTesting/IngressEgress/FlushPolicyTestMatrixBase.cs b/Sources/Test/SimpleTesting/IngressEgress/FlushPolicyTestMatrixBase.cs index e0af14413..bac4766d5 100644 --- a/Sources/Test/SimpleTesting/IngressEgress/FlushPolicyTestMatrixBase.cs +++ b/Sources/Test/SimpleTesting/IngressEgress/FlushPolicyTestMatrixBase.cs @@ -12,7 +12,7 @@ namespace SimpleTesting.Flush { - public class FlushTestBase : TestWithConfigSettingsAndMemoryLeakDetection + public abstract class FlushTestBase : TestWithConfigSettingsAndMemoryLeakDetection { private const int IntervalLength = 5; private const int BatchSize = 10; // TODO: this will be identical for FlushPolicy.None and FlushOnBatchBoundary without some filter operator @@ -55,7 +55,7 @@ public void FilterTest() OnIngress(inputSubject, StreamEvent.CreatePunctuation(i)); // Make sure we don't have any pending events we expected to be egressed at this point - Assert.IsTrue(this.expectedOutput.Count == 0); + Assert.IsEmpty(this.expectedOutput); } OnCompleted(inputSubject); @@ -115,7 +115,7 @@ private void MoveFilteredBatchBatchToOutput() private void OnEgress(StreamEvent egressEvent) { - Assert.IsTrue(this.expectedOutput.Count > 0); + Assert.IsNotEmpty(this.expectedOutput); var expectedEvent = this.expectedOutput.Dequeue(); Assert.IsTrue(expectedEvent.Equals(egressEvent)); diff --git a/Sources/Test/SimpleTesting/MultiStringTests.cs b/Sources/Test/SimpleTesting/MultiStringTests.cs index 4477d88ec..e6d3b6618 100644 --- a/Sources/Test/SimpleTesting/MultiStringTests.cs +++ b/Sources/Test/SimpleTesting/MultiStringTests.cs @@ -609,11 +609,11 @@ public void MultiStringRegex1() { if ((result.col[i >> 6] & (1L << (i & 0x3f))) == 0) { - Assert.IsTrue(input[i].Contains(pattern)); + Assert.Contains(pattern, input[i]); } else { - Assert.IsFalse(input[i].Contains(pattern)); + Assert.DoesNotContain(pattern, input[i]); } } inBV.ReturnClear(); diff --git a/Sources/Test/SimpleTesting/Partitioned/PartitionedIngressAndEgressTestMatrixBases.cs b/Sources/Test/SimpleTesting/Partitioned/PartitionedIngressAndEgressTestMatrixBases.cs index f84057087..f67deef83 100644 --- a/Sources/Test/SimpleTesting/Partitioned/PartitionedIngressAndEgressTestMatrixBases.cs +++ b/Sources/Test/SimpleTesting/Partitioned/PartitionedIngressAndEgressTestMatrixBases.cs @@ -11,7 +11,7 @@ namespace SimpleTesting.PartitionedIngressAndEgress { - public class TriPartitionedOrderedTestsBase : TestWithConfigSettingsAndMemoryLeakDetection + public abstract class TriPartitionedOrderedTestsBase : TestWithConfigSettingsAndMemoryLeakDetection { internal TriPartitionedOrderedTestsBase( ConfigModifier config, @@ -86,8 +86,8 @@ private void ValidateOutput(IList input, IList data.Length, "Flush should push all events out."); + Assert.IsGreaterThan(data.Length, res.Count, "Flush should push all events out."); j.OnCompleted(); } @@ -748,7 +748,7 @@ public void AlterLifeTimeWithFlush() { } - Assert.IsTrue(res.Count > 0, "There should be some results."); + Assert.IsNotEmpty(res, "There should be some results."); } [TestMethod, TestCategory("Gated")] @@ -801,7 +801,7 @@ public void AlterLifeTimeWithFlushDoubles() { } - Assert.IsTrue(res.Count > 0, "There should be some results."); + Assert.IsNotEmpty(res, "There should be some results."); } [TestMethod, TestCategory("Gated")] diff --git a/Sources/Test/SimpleTesting/Serializer/SurrogateTests.cs b/Sources/Test/SimpleTesting/Serializer/SurrogateTests.cs index 975e98e97..ce2bb5b5b 100644 --- a/Sources/Test/SimpleTesting/Serializer/SurrogateTests.cs +++ b/Sources/Test/SimpleTesting/Serializer/SurrogateTests.cs @@ -108,7 +108,7 @@ public void SurrogateTest() input2.OnCompleted(); - Assert.AreEqual(2, output2.Count); + Assert.HasCount(2, output2); Assert.AreEqual(1, output2[0].Payload.GetValue()); Assert.AreEqual(StreamEvent.InfinitySyncTime, output2[1].SyncTime); } diff --git a/Sources/Test/SimpleTesting/SimpleTesting.csproj b/Sources/Test/SimpleTesting/SimpleTesting.csproj index f1b901102..8cf918975 100644 --- a/Sources/Test/SimpleTesting/SimpleTesting.csproj +++ b/Sources/Test/SimpleTesting/SimpleTesting.csproj @@ -1,17 +1,17 @@  - net472;netcoreapp3.1 + net10.0 AnyCPU - - - - - - + + + + + +