public void CountUnitsOfWorkAreReportedAccurately() { const int expectedUnitsOfWork = 1000; const int countThreads = 5; var iterativeExerciserUnitsOfWorkExecuted = 0; var iterativeExerciserResult = IterativeExerciser.Create() .UsingThreads(countThreads) .PerformUnitOfWorkNTimes(expectedUnitsOfWork) .DoThisUnitOfWork(() => { Interlocked.Increment(ref iterativeExerciserUnitsOfWorkExecuted); }) .ExecAll(); var workQueueExerciserUnitsOfWorkExecuted = 0; var workQueueExerciserResult = WorkQueueExerciser.Create() .UsingThreads(countThreads) .WithWorkQueueSize(expectedUnitsOfWork) .DoThisUnitOfWork(() => { Interlocked.Increment(ref workQueueExerciserUnitsOfWorkExecuted); }) .ExecAll(); var throughputExerciserUnitsOfWorkExercised = 0; var throughputExerciserResult = ThroughputExerciser.Create() .UsingThreads(countThreads) .ForDuration(100) .DoThisUnitOfWork(() => { Interlocked.Increment(ref throughputExerciserUnitsOfWorkExercised); }) .ExecAll(); NrAssert.Multiple( () => Assert.AreEqual(expectedUnitsOfWork * countThreads, iterativeExerciserResult.CountUnitsOfWorkPerformed), () => Assert.AreEqual(expectedUnitsOfWork * countThreads, iterativeExerciserUnitsOfWorkExecuted), () => Assert.AreEqual(expectedUnitsOfWork, workQueueExerciserResult.CountUnitsOfWorkPerformed), () => Assert.AreEqual(expectedUnitsOfWork, workQueueExerciserUnitsOfWorkExecuted), () => Assert.AreEqual(throughputExerciserUnitsOfWorkExercised, throughputExerciserResult.CountUnitsOfWorkPerformed) ); }
public void ExerciserMethodsAreCalledCorrectNumberOfTimes() { const int expectedUnitsOfWork = 100; const int countThreads = 5; ConcurrentBag <DateTime> setupTimes = null; ConcurrentBag <DateTime> beforeUOWTimes = null; ConcurrentBag <DateTime> uowTimes = null; ConcurrentBag <DateTime> afterUowTimes = null; ConcurrentBag <DateTime> teardownTimes = null; var iterativeExerciser = IterativeExerciser.Create() .UsingThreads(countThreads) .PerformUnitOfWorkNTimes(expectedUnitsOfWork) .DoThisToSetup(() => setupTimes.Add(DateTime.Now)) .DoThisBeforeEachUnitOfWork(() => beforeUOWTimes.Add(DateTime.Now)) .DoThisUnitOfWork(() => uowTimes.Add(DateTime.Now)) .DoThisAfterEachUnitOfWork(() => afterUowTimes.Add(DateTime.Now)) .DoThisToTearDown(() => teardownTimes.Add(DateTime.Now)); var workQueueExerciser = WorkQueueExerciser.Create() .UsingThreads(countThreads) .WithWorkQueueSize(expectedUnitsOfWork) .DoThisToSetup(() => setupTimes.Add(DateTime.Now)) .DoThisBeforeEachUnitOfWork(() => beforeUOWTimes.Add(DateTime.Now)) .DoThisUnitOfWork(() => uowTimes.Add(DateTime.Now)) .DoThisAfterEachUnitOfWork(() => afterUowTimes.Add(DateTime.Now)) .DoThisToTearDown(() => teardownTimes.Add(DateTime.Now)); var throughputExerciser = ThroughputExerciser.Create() .UsingThreads(countThreads) .ForDuration(100) .DoThisToSetup(() => setupTimes.Add(DateTime.Now)) .DoThisBeforeEachUnitOfWork(() => beforeUOWTimes.Add(DateTime.Now)) .DoThisUnitOfWork(() => uowTimes.Add(DateTime.Now)) .DoThisAfterEachUnitOfWork(() => afterUowTimes.Add(DateTime.Now)) .DoThisToTearDown(() => teardownTimes.Add(DateTime.Now)); foreach (var exerciser in new Exerciser[] { iterativeExerciser, workQueueExerciser, throughputExerciser }) { setupTimes = new ConcurrentBag <DateTime>(); beforeUOWTimes = new ConcurrentBag <DateTime>(); uowTimes = new ConcurrentBag <DateTime>(); afterUowTimes = new ConcurrentBag <DateTime>(); teardownTimes = new ConcurrentBag <DateTime>(); var exerciserResult = exerciser.ExecAll(); NrAssert.Multiple( () => Assert.AreEqual(1, setupTimes.Count), () => Assert.AreEqual(exerciserResult.CountUnitsOfWorkPerformed, beforeUOWTimes.Count, $"{exerciser.GetType().FullName}, beforeUOW"), () => Assert.AreEqual(exerciserResult.CountUnitsOfWorkPerformed, uowTimes.Count, $"{exerciser.GetType().FullName}, the Actual UOW"), () => Assert.AreEqual(exerciserResult.CountUnitsOfWorkPerformed, afterUowTimes.Count, $"{exerciser.GetType().FullName}, After UOW"), () => Assert.AreEqual(1, teardownTimes.Count)); } }
public void UnitOfWorkVariablesAreBeingCapturedCorrectly() { const int expectedUnitsOfWork = 100; const int countThreads = 5; //Update counters based on the global or local counter //later we will check to make sure that they are all set to 1 ConcurrentDictionary <int, ConcurrentDictionary <int, int[]> > localCounters = null; ConcurrentDictionary <int, int[]> globalResultCounters = null; var iterativeExerciser = IterativeExerciser.Create() .UsingThreads(countThreads) .PerformUnitOfWorkNTimes(expectedUnitsOfWork) .DoThisBeforeEachUnitOfWork((threadId, uowIdLocal, uowIdGlobal) => { Interlocked.Increment(ref localCounters[threadId].GetOrAdd(uowIdLocal, new int[3])[0]); Interlocked.Increment(ref globalResultCounters.GetOrAdd(uowIdGlobal, new int[3])[0]); }) .DoThisUnitOfWork((threadId, uowIdLocal, uowIdGlobal) => { Interlocked.Increment(ref localCounters[threadId].GetOrAdd(uowIdLocal, new int[3])[1]); Interlocked.Increment(ref globalResultCounters.GetOrAdd(uowIdGlobal, new int[3])[1]); }) .DoThisAfterEachUnitOfWork((threadId, uowIdLocal, uowIdGlobal) => { Interlocked.Increment(ref localCounters[threadId].GetOrAdd(uowIdLocal, new int[3])[2]); Interlocked.Increment(ref globalResultCounters.GetOrAdd(uowIdGlobal, new int[3])[2]); }); var workQueueExerciser = WorkQueueExerciser.Create() .UsingThreads(countThreads) .WithWorkQueueSize(expectedUnitsOfWork) .DoThisBeforeEachUnitOfWork((threadId, uowIdLocal, uowIdGlobal) => { Interlocked.Increment(ref localCounters[threadId].GetOrAdd(uowIdLocal, new int[3])[0]); Interlocked.Increment(ref globalResultCounters.GetOrAdd(uowIdGlobal, new int[3])[0]); }) .DoThisUnitOfWork((threadId, uowIdLocal, uowIdGlobal) => { Interlocked.Increment(ref localCounters[threadId].GetOrAdd(uowIdLocal, new int[3])[1]); Interlocked.Increment(ref globalResultCounters.GetOrAdd(uowIdGlobal, new int[3])[1]); }) .DoThisAfterEachUnitOfWork((threadId, uowIdLocal, uowIdGlobal) => { Interlocked.Increment(ref localCounters[threadId].GetOrAdd(uowIdLocal, new int[3])[2]); Interlocked.Increment(ref globalResultCounters.GetOrAdd(uowIdGlobal, new int[3])[2]); }); var throughputExerciser = ThroughputExerciser.Create() .UsingThreads(countThreads) .ForDuration(100) .DoThisBeforeEachUnitOfWork((threadId, uowIdLocal, uowIdGlobal) => { Interlocked.Increment(ref localCounters[threadId].GetOrAdd(uowIdLocal, new int[3])[0]); Interlocked.Increment(ref globalResultCounters.GetOrAdd(uowIdGlobal, new int[3])[0]); }) .DoThisUnitOfWork((threadId, uowIdLocal, uowIdGlobal) => { Interlocked.Increment(ref localCounters[threadId].GetOrAdd(uowIdLocal, new int[3])[1]); Interlocked.Increment(ref globalResultCounters.GetOrAdd(uowIdGlobal, new int[3])[1]); }) .DoThisAfterEachUnitOfWork((threadId, uowIdLocal, uowIdGlobal) => { Interlocked.Increment(ref localCounters[threadId].GetOrAdd(uowIdLocal, new int[3])[2]); Interlocked.Increment(ref globalResultCounters.GetOrAdd(uowIdGlobal, new int[3])[2]); }); foreach (var exerciser in new Exerciser[] { iterativeExerciser, workQueueExerciser, throughputExerciser }) { localCounters = new ConcurrentDictionary <int, ConcurrentDictionary <int, int[]> >(); globalResultCounters = new ConcurrentDictionary <int, int[]>(); foreach (var thread in localCounters) { foreach (var uow in thread.Value) { NrAssert.Multiple( () => Assert.AreEqual(1, uow.Value[0], $"{exerciser.GetType().FullName}, threadID: {thread.Key}, uowIdLocal: {uow.Key}, BeforeUOW"), () => Assert.AreEqual(1, uow.Value[1], $"{exerciser.GetType().FullName}, threadID: {thread.Key}, uowIdLocal: {uow.Key}, TheUOW"), () => Assert.AreEqual(1, uow.Value[2], $"{exerciser.GetType().FullName}, threadID: {thread.Key}, uowIdLocal: {uow.Key}, AfterUOW")); } } foreach (var uow in globalResultCounters) { NrAssert.Multiple( () => Assert.AreEqual(1, uow.Value[0], $"{exerciser.GetType().FullName}, uowIdGlobal {uow.Key}, BeforeUOW"), () => Assert.AreEqual(1, uow.Value[1], $"{exerciser.GetType().FullName}, uowIdGlobal {uow.Key}, TheUOW"), () => Assert.AreEqual(1, uow.Value[2], $"{exerciser.GetType().FullName}, uowIdGlobal {uow.Key}, AfterUOW")); } } }
public void ExerciserMethodsAreCalledInCorrectOrder() { const int expectedUnitsOfWork = 10; const int countThreads = 5; ConcurrentBag <DateTime> setupTimes = null; ConcurrentBag <DateTime> beforeUOWTimes = null; ConcurrentBag <DateTime> uowTimes = null; ConcurrentBag <DateTime> afterUowTimes = null; ConcurrentBag <DateTime> teardownTimes = null; var iterativeExerciser = IterativeExerciser.Create() .UsingThreads(countThreads) .PerformUnitOfWorkNTimes(expectedUnitsOfWork) .DoThisToSetup(() => { setupTimes.Add(DateTime.Now); Thread.Sleep(50); }) .DoThisBeforeEachUnitOfWork(() => { beforeUOWTimes.Add(DateTime.Now); Thread.Sleep(10); }) .DoThisUnitOfWork(() => uowTimes.Add(DateTime.Now)) .DoThisAfterEachUnitOfWork(() => { Thread.Sleep(10); afterUowTimes.Add(DateTime.Now); }) .DoThisToTearDown(() => { Thread.Sleep(50); teardownTimes.Add(DateTime.Now); }); var workQueueExerciser = WorkQueueExerciser.Create() .UsingThreads(countThreads) .WithWorkQueueSize(expectedUnitsOfWork) .DoThisToSetup(() => { setupTimes.Add(DateTime.Now); Thread.Sleep(50); }) .DoThisBeforeEachUnitOfWork(() => { beforeUOWTimes.Add(DateTime.Now); Thread.Sleep(10); }) .DoThisUnitOfWork(() => uowTimes.Add(DateTime.Now)) .DoThisAfterEachUnitOfWork(() => { Thread.Sleep(10); afterUowTimes.Add(DateTime.Now); }) .DoThisToTearDown(() => { Thread.Sleep(50); teardownTimes.Add(DateTime.Now); }); var throughputExerciser = ThroughputExerciser.Create() .UsingThreads(countThreads) .ForDuration(100) .DoThisToSetup(() => { setupTimes.Add(DateTime.Now); Thread.Sleep(50); }) .DoThisBeforeEachUnitOfWork(() => { beforeUOWTimes.Add(DateTime.Now); Thread.Sleep(10); }) .DoThisUnitOfWork(() => uowTimes.Add(DateTime.Now)) .DoThisAfterEachUnitOfWork(() => { Thread.Sleep(10); afterUowTimes.Add(DateTime.Now); }) .DoThisToTearDown(() => { Thread.Sleep(50); teardownTimes.Add(DateTime.Now); }); foreach (var exerciser in new Exerciser[] { iterativeExerciser, workQueueExerciser, throughputExerciser }) { setupTimes = new ConcurrentBag <DateTime>(); beforeUOWTimes = new ConcurrentBag <DateTime>(); uowTimes = new ConcurrentBag <DateTime>(); afterUowTimes = new ConcurrentBag <DateTime>(); teardownTimes = new ConcurrentBag <DateTime>(); var exerciserResult = exerciser.ExecAll(); NrAssert.Multiple( () => Assert.Greater(beforeUOWTimes.Min(), setupTimes.Max(), $"{exerciser.GetType().FullName} BeforeUOW detected before end of Setup"), () => Assert.Greater(uowTimes.Min(), beforeUOWTimes.Min(), $"{exerciser.GetType().FullName} UOW detected before end of BeforeUOW"), () => Assert.Greater(afterUowTimes.Max(), uowTimes.Max(), $"{exerciser.GetType().FullName} AfterUOW detected before end of UOW"), () => Assert.Greater(teardownTimes.Min(), afterUowTimes.Max(), $"{exerciser.GetType().FullName} Terdown detected before end of AfterUOW")); } }