public void TestBatcherLatencyInitialBatch() { var doneEvent = new ManualResetEvent(false); inboxCapacity = 100; processorDelay = 500; var timeProcessed = default(DateTime); var scheduler = new SingleThreadTaskScheduler(); var batcher = new Batcher<string>( new TaskFactory(scheduler), inboxCapacity, processorDelay, itemsToProcess => { Log.V(Tag, "process called with: " + itemsToProcess); timeProcessed = DateTime.UtcNow; doneEvent.Set(); }); var objectsToQueue = new List<string>(); for (var i = 0; i < inboxCapacity + 1; i++) { objectsToQueue.Add(i.ToString()); } var timeQueued = DateTime.UtcNow; batcher.QueueObjects(objectsToQueue); var success = doneEvent.WaitOne(TimeSpan.FromSeconds(35)); Assert.IsTrue(success); var delta = (timeProcessed - timeQueued).TotalMilliseconds; Assert.IsTrue(delta >= 0); // we want the delta between the time it was queued until the // time it was processed to be as small as possible. since // there is some overhead, rather than using a hardcoded number // express it as a ratio of the processor delay, asserting // that the entire processor delay never kicked in. int acceptableDelta = processorDelay - 1; Log.V(Tag, string.Format("TestBatcherLatencyInitialBatch : delta: {0}", delta)); Assert.IsTrue(delta < acceptableDelta); }
/// <summary> /// Creates a new <see cref="Couchbase.Lite.Replication"/> that will pull from the source <see cref="Couchbase.Lite.Database"/> at the given url. /// </summary> /// <returns>A new <see cref="Couchbase.Lite.Replication"/> that will pull from the source Database at the given url.</returns> /// <param name="url">The url of the source Database.</param> public Replication CreatePullReplication(Uri url) { var scheduler = new SingleThreadTaskScheduler(); //TaskScheduler.FromCurrentSynchronizationContext(); return new Puller(this, url, false, new TaskFactory(scheduler)); }
public void TestBatcherBatchSize5() { doneSignal = new CountDownLatch(10); inboxCapacity = 10; processorDelay = 1000; var scheduler = new SingleThreadTaskScheduler(); var batcher = new Batcher<string>(new TaskFactory(scheduler), inboxCapacity, processorDelay, TestBatcherBatchSize5Processor); var objectsToQueue = new List<string>(); for (var i = 0; i < inboxCapacity * 10; i++) { objectsToQueue.Add(i.ToString()); if (objectsToQueue.Count == 5) { batcher.QueueObjects(objectsToQueue); objectsToQueue.Clear(); } } var success = doneSignal.Await(TimeSpan.FromSeconds(35)); Assert.IsTrue(success); }
public void TestBatcherLatencyTrickleIn() { doneSignal = new CountDownLatch(10); inboxCapacity = 100; processorDelay = 500; maxObservedDelta = -1L; var scheduler = new SingleThreadTaskScheduler(); var batcher = new Batcher<long>(new TaskFactory(scheduler), inboxCapacity, processorDelay, TestBatcherLatencyTrickleInProcessor); for (var i = 0; i < 10; i++) { var objectsToQueue = new List<long>(); objectsToQueue.Add(Runtime.CurrentTimeMillis()); batcher.QueueObjects(objectsToQueue); System.Threading.Thread.Sleep(1000); } var success = doneSignal.Await(TimeSpan.FromSeconds(35)); Assert.IsTrue(success); // we want the max observed delta between the time it was queued until the // time it was processed to be as small as possible. since // there is some overhead, rather than using a hardcoded number // express it as a ratio of 1/4th the processor delay, asserting // that the entire processor delay never kicked in. int acceptableMaxDelta = processorDelay - 1; Log.V(Tag, string.Format("TestBatcherLatencyTrickleIn : maxObservedDelta: {0}", maxObservedDelta)); Assert.IsTrue((maxObservedDelta < acceptableMaxDelta)); }
private void RunChangeTrackerTransientError( ChangeTrackerMode mode, Int32 errorCode, string statusMessage, Int32 numExpectedChangeCallbacks) { var changeTrackerFinishedSignal = new CountDownLatch(1); var changeReceivedSignal = new CountDownLatch(numExpectedChangeCallbacks); var client = new ChangeTrackerTestClient(changeTrackerFinishedSignal, changeReceivedSignal); MockHttpRequestHandler.HttpResponseDelegate sentinal = RunChangeTrackerTransientErrorDefaultResponder(); var responders = new List<MockHttpRequestHandler.HttpResponseDelegate>(); responders.Add(RunChangeTrackerTransientErrorDefaultResponder()); responders.Add(MockHttpRequestHandler.TransientErrorResponder(errorCode, statusMessage)); MockHttpRequestHandler.HttpResponseDelegate chainResponder = (request) => { if (responders.Count > 0) { var responder = responders[0]; responders.RemoveAt(0); return responder(request); } return sentinal(request); }; var handler = client.HttpRequestHandler; handler.SetResponder("_changes", chainResponder); var testUrl = GetReplicationURL(); var scheduler = new SingleThreadTaskScheduler(); var changeTracker = new ChangeTracker(testUrl, mode, 0, false, client, new TaskFactory(scheduler)); changeTracker.UsePost = IsSyncGateway(testUrl); changeTracker.Start(); var success = changeReceivedSignal.Await(TimeSpan.FromSeconds(30)); Assert.IsTrue(success); changeTracker.Stop(); success = changeTrackerFinishedSignal.Await(TimeSpan.FromSeconds(30)); Assert.IsTrue(success); }
private void TestChangeTrackerBackoff(MockHttpClientFactory httpClientFactory) { var changeTrackerFinishedSignal = new CountDownLatch(1); var client = new ChangeTrackerTestClient(changeTrackerFinishedSignal, null); client.HttpClientFactory = httpClientFactory; var testUrl = GetReplicationURL(); var scheduler = new SingleThreadTaskScheduler(); var changeTracker = new ChangeTracker(testUrl, ChangeTrackerMode.LongPoll, 0, false, client, new TaskFactory(scheduler)); changeTracker.UsePost = IsSyncGateway(testUrl); changeTracker.Start(); // sleep for a few seconds Thread.Sleep(5 * 1000); // make sure we got less than 10 requests in those 10 seconds (if it was hammering, we'd get a lot more) var handler = client.HttpRequestHandler; Assert.IsTrue(handler.CapturedRequests.Count < 25); Assert.IsTrue(changeTracker.backoff.NumAttempts > 0, "Observed attempts: {0}".Fmt(changeTracker.backoff.NumAttempts)); handler.ClearResponders(); handler.AddResponderReturnEmptyChangesFeed(); // at this point, the change tracker backoff should cause it to sleep for about 3 seconds // and so lets wait 3 seconds until it wakes up and starts getting valid responses Thread.Sleep(3 * 1000); // now find the delta in requests received in a 2s period int before = handler.CapturedRequests.Count; Thread.Sleep(2 * 1000); int after = handler.CapturedRequests.Count; // assert that the delta is high, because at this point the change tracker should // be hammering away Assert.IsTrue((after - before) > 25); // the backoff numAttempts should have been reset to 0 Assert.IsTrue(changeTracker.backoff.NumAttempts == 0); changeTracker.Stop(); var success = changeTrackerFinishedSignal.Await(TimeSpan.FromSeconds(30)); Assert.IsTrue(success); }
private void ChangeTrackerTestWithMode(ChangeTrackerMode mode) { var changeTrackerFinishedSignal = new CountDownLatch(1); var changeReceivedSignal = new CountDownLatch(1); var client = new ChangeTrackerTestClient(changeTrackerFinishedSignal, changeReceivedSignal); client.ReceivedChangeDelegate = (IDictionary<string, object> change) => { Assert.IsTrue(change.ContainsKey("seq")); Assert.AreEqual("1", change["seq"]); }; var handler = client.HttpRequestHandler; handler.SetResponder("_changes", (request) => { var json = "{\"results\":[\n" + "{\"seq\":\"1\",\"id\":\"doc1-138\",\"changes\":[{\"rev\":\"1-82d\"}]}],\n" + "\"last_seq\":\"*:50\"}"; return MockHttpRequestHandler.GenerateHttpResponseMessage(HttpStatusCode.OK, null, json); }); var testUrl = GetReplicationURL(); var scheduler = new SingleThreadTaskScheduler(); var changeTracker = new ChangeTracker(testUrl, mode, 0, false, client, new TaskFactory(scheduler)); changeTracker.UsePost = IsSyncGateway(testUrl); changeTracker.Start(); var success = changeReceivedSignal.Await(TimeSpan.FromSeconds(30)); Assert.IsTrue(success); changeTracker.Stop(); success = changeTrackerFinishedSignal.Await(TimeSpan.FromSeconds(30)); Assert.IsTrue(success); }