Esempio n. 1
0
        public void ClientDisconnected_ServerRaisesErrorMessage()
        {
            var failedOrigin = IntegrationTestsHelper
                               .GetOriginBuilder()
                               .UseSerializer(IntegrationTestsHelper.GetThrowsSerializationRuleFor <string>());

            using (var tcpPair = new TcpConnectionPair <ITestContract, ITestContract, TestContractMock>
                                     (failedOrigin, IntegrationTestsHelper.GetProxyBuilder()))
            {
                var awaiter = new EventAwaiter <ClientDisconnectEventArgs <ITestContract, TcpChannel> >();
                tcpPair.Server.Disconnected += awaiter.EventRaised;

                //provokes exception at origin-side serialization
                try
                {
                    tcpPair.ProxyContract.Ask("some string");
                }
                catch (RemoteSerializationException) {}

                var receivedArgs = awaiter.WaitOneOrDefault(500);
                //Client disconnected event is expected
                Assert.IsNotNull(receivedArgs);
                Assert.IsNotNull(receivedArgs.ErrorMessageOrNull);
                Assert.AreEqual(ErrorType.SerializationError, receivedArgs.ErrorMessageOrNull.ErrorType);
            }
        }
        public async Task TestInitializeAsync()
        {
            if (this.ClassData.monitoredCollectionInfo == null)
            {
                try
                {
                    if (this.ClassData.monitoredCollectionInfo == null)
                    {
                        this.ClassData.leaseCollectionInfoTemplate = await TestClassInitializeAsync(this, $"data_{this.GetType().Name}");
                    }
                }
                catch (Exception ex)
                {
                    Debug.Write(ex);
                    throw;
                }
            }

            this.LeaseCollectionInfo = new DocumentCollectionInfo(this.ClassData.leaseCollectionInfoTemplate);
            this.LeaseCollectionInfo.CollectionName = $"leases_{this.GetType().Name}_{Guid.NewGuid().ToString()}";

            var leaseCollection = new DocumentCollection {
                Id = this.LeaseCollectionInfo.CollectionName
            };

            using (var client = new DocumentClient(this.LeaseCollectionInfo.Uri, this.LeaseCollectionInfo.MasterKey, this.LeaseCollectionInfo.ConnectionPolicy))
            {
                await IntegrationTestsHelper.CreateDocumentCollectionAsync(client, this.LeaseCollectionInfo.DatabaseName, leaseCollection, leaseOfferThroughput);
            }
        }
        public async Task InitializeAsync()
        {
            try
            {
                await this.CreateMonitoredCollectionAsync($"data_{this.GetType().Name}");
            }
            catch (Exception ex)
            {
                Debug.WriteLine(ex);
                throw;
            }

            this.LeaseCollectionInfo.CollectionName = $"leases_{this.GetType().Name}_{Guid.NewGuid().ToString()}";

            var leaseCollection = new DocumentCollection
            {
                Id = this.LeaseCollectionInfo.CollectionName,
            };

            if (this.IsPartitionedLeaseCollection)
            {
                leaseCollection.PartitionKey = new PartitionKeyDefinition {
                    Paths = { "/id" }
                };
            }

            using (var client = new DocumentClient(this.LeaseCollectionInfo.Uri, this.LeaseCollectionInfo.MasterKey, this.LeaseCollectionInfo.ConnectionPolicy))
            {
                await IntegrationTestsHelper.CreateDocumentCollectionAsync(client, this.LeaseCollectionInfo.DatabaseName, leaseCollection, leaseOfferThroughput);
            }
        }
        public void HundredOf2mbPacket_transmitsViaTcp_oneByOne()
        {
            var origin = TntBuilder
                         .UseContract <ISingleMessageContract <Company>, SingleMessageContract <Company> >()
                         .SetMaxAnsDelay(5 * 60 * 1000);
            var proxy = TntBuilder
                        .UseContract <ISingleMessageContract <Company> >()
                        .SetMaxAnsDelay(5 * 60 * 1000);

            using (var tcpPair = new TcpConnectionPair
                                 <ISingleMessageContract <Company>,
                                  ISingleMessageContract <Company>,
                                  SingleMessageContract <Company> >(origin, proxy))
            {
                var receivedList = new List <Company>(200);

                tcpPair.OriginContract.SayCalled
                    += (Sender, received) => receivedList.Add(received);
                var company   = IntegrationTestsHelper.CreateCompany(2000);
                int sendCount = 100;
                for (int i = 0; i < sendCount; i++)
                {
                    tcpPair.ProxyConnection.Contract.Ask(company);
                }
                Assert.AreEqual(sendCount, receivedList.Count);
                foreach (var received in receivedList)
                {
                    received.AssertIsSameTo(company);
                }
            }
        }
Esempio n. 5
0
        public async Task CountDocumentsInCollection_TwoHosts()
        {
            await this.InitializeDocumentsAsync();

            int partitionKeyRangeCount = await IntegrationTestsHelper.GetPartitionCount(this.MonitoredCollectionInfo);

            Assert.True(partitionKeyRangeCount > 1, "Prerequisite failed: expected monitored collection with at least 2 partitions.");

            int processedCount   = 0;
            var allDocsProcessed = new ManualResetEvent(false);

            var observerFactory = new TestObserverFactory(
                (ChangeFeedObserverContext context, IReadOnlyList <Document> docs) =>
            {
                int newCount = Interlocked.Add(ref processedCount, docs.Count);
                if (newCount == documentCount)
                {
                    allDocsProcessed.Set();
                }
                return(Task.CompletedTask);
            });

            var host1 = new ChangeFeedEventHost(
                Guid.NewGuid().ToString(),
                this.MonitoredCollectionInfo,
                this.LeaseCollectionInfo,
                new ChangeFeedOptions {
                StartFromBeginning = true
            },
                new ChangeFeedHostOptions {
                MaxPartitionCount = partitionKeyRangeCount / 2
            });
            await host1.RegisterObserverFactoryAsync(observerFactory);

            var host2 = new ChangeFeedEventHost(
                Guid.NewGuid().ToString(),
                this.MonitoredCollectionInfo,
                this.LeaseCollectionInfo,
                new ChangeFeedOptions {
                StartFromBeginning = true
            },
                new ChangeFeedHostOptions {
                MaxPartitionCount = partitionKeyRangeCount - partitionKeyRangeCount / 2
            });
            await host2.RegisterObserverFactoryAsync(observerFactory);

            allDocsProcessed.WaitOne(changeWaitTimeout + changeWaitTimeout);

            try
            {
                Assert.True(documentCount == processedCount, $"Wrong processedCount {documentCount} {processedCount}");
            }
            finally
            {
                await host1.UnregisterObserversAsync();

                await host2.UnregisterObserversAsync();
            }
        }
        private async Task <DiffData> CallSetData(string url, string data)
        {
            var requestBody = IntegrationTestsHelper.BuildSetDataRequest(data);

            var response = await _client.PostAsync(url, requestBody);

            return(JsonConvert.DeserializeObject <DiffData>(await response.Content.ReadAsStringAsync()));
        }
        private async Task <ErrorResponse> EndToEndTestWithError(string id, string leftData, string rightData)
        {
            await SetupData(id, leftData, rightData);

            var diffResponse = await _client.GetAsync(IntegrationTestsHelper.GetDiffUrl(id));

            return(JsonConvert.DeserializeObject <ErrorResponse>(await diffResponse.Content.ReadAsStringAsync()));
        }
        public void DeserializationThrowsRule_throws()
        {
            //Just check the Moq generator behaves as expected
            var rule         = IntegrationTestsHelper.GetThrowsDeserializationRuleFor <string>();
            var deserializer = rule.GetDeserializer(typeof(string), DeserializerFactory.CreateDefault());

            Assert.Throws <Exception>(() => deserializer.Deserialize(new MemoryStream(), 0));
        }
 protected override async Task FinishTestClassInitializeAsync()
 {
     using (var client = new DocumentClient(this.ClassData.monitoredCollectionInfo.Uri, this.ClassData.monitoredCollectionInfo.MasterKey, this.ClassData.monitoredCollectionInfo.ConnectionPolicy))
     {
         var collectionUri = UriFactory.CreateDocumentCollectionUri(this.ClassData.monitoredCollectionInfo.DatabaseName, this.ClassData.monitoredCollectionInfo.CollectionName);
         await IntegrationTestsHelper.CreateDocumentsAsync(client, collectionUri, documentCount);
     }
 }
Esempio n. 10
0
        private async Task InitializeDocumentsAsync()
        {
            using (var client = new DocumentClient(this.MonitoredCollectionInfo.Uri, this.MonitoredCollectionInfo.MasterKey, this.MonitoredCollectionInfo.ConnectionPolicy))
            {
                var collectionUri = UriFactory.CreateDocumentCollectionUri(this.MonitoredCollectionInfo.DatabaseName, this.MonitoredCollectionInfo.CollectionName);

                await IntegrationTestsHelper.CreateDocumentsAsync(client, collectionUri, documentCount);
            }
        }
        public async Task WhenLeasesHaveContinuationTokenNullReturn0()
        {
            // Cleanup the test collection to avoid other tests' documents causing issues with StartFromBeginning
            await this.ResetTestCollection();

            int documentCount  = 1;
            int partitionCount = await IntegrationTestsHelper.GetPartitionCount(this.ClassData.monitoredCollectionInfo);

            int openedCount = 0, processedCount = 0;
            var allObserversStarted = new ManualResetEvent(false);
            var allDocsProcessed    = new ManualResetEvent(false);

            var observerFactory = new TestObserverFactory(
                context =>
            {
                int newCount = Interlocked.Increment(ref openedCount);
                if (newCount == partitionCount)
                {
                    allObserversStarted.Set();
                }
                return(Task.CompletedTask);
            },
                null,
                (ChangeFeedObserverContext context, IReadOnlyList <Document> docs) =>
            {
                int newCount = Interlocked.Add(ref processedCount, docs.Count);
                if (newCount == documentCount)
                {
                    allDocsProcessed.Set();
                }
                return(Task.CompletedTask);
            });

            var hostName = Guid.NewGuid().ToString();

            // We create a host to initialize the leases with ContinuationToken null
            var host = new ChangeFeedEventHost(
                hostName,
                this.ClassData.monitoredCollectionInfo,
                this.LeaseCollectionInfo,
                new ChangeFeedOptions {
                StartFromBeginning = false
            },
                new ChangeFeedHostOptions());

            // Initialize leases
            await host.RegisterObserverFactoryAsync(observerFactory);

            // Stop host, this leaves the leases with ContinuationToken null state
            await host.UnregisterObserversAsync();

            // Since the leases have ContinuationToken null state, the estimator will use StartFromBeginning and pick-up the changes that happened from the start
            long estimation = await host.GetEstimatedRemainingWork();

            Assert.Equal(0, estimation);
        }
Esempio n. 12
0
        public void WordFilesRepository_Should_Store_Image_As_Answer()
        {
            var wordDocRepo = new WordFilesRepository();

            var rootPath = IntegrationTestsHelper.GetFullResourcePath("integration-test-question-image.docx");

            var doc = wordDocRepo.GetDocument(rootPath);

            doc.Tables.Should().HaveCount(1);
        }
        private async Task SetupData(string id, string leftData, string rightData)
        {
            var leftResponse = await CallSetData(IntegrationTestsHelper.GetSetLeftUrl(id), leftData);

            var rightResponse = await CallSetData(IntegrationTestsHelper.GetSetRightUrl(id), rightData);

            Assert.Equal(leftData, leftResponse.Data);
            Assert.Equal(id, leftResponse.RequestId);

            Assert.Equal(rightData, rightResponse.Data);
            Assert.Equal(id, rightResponse.RequestId);
        }
Esempio n. 14
0
        private static void SerializeAndDeserializeProtobuffMessage(int companySize)
        {
            var company = IntegrationTestsHelper.CreateCompany(companySize);

            using (var stream = new MemoryStream())
            {
                var serializer = new TNT.Presentation.Serializers.ProtoSerializer <Company>();
                serializer.SerializeT(company, stream);
                stream.Position = 0;
                var deserializer = new TNT.Presentation.Deserializers.ProtoDeserializer <Company>();
                var deserialized = deserializer.DeserializeT(stream, (int)stream.Length);
                company.AssertIsSameTo(deserialized);
            }
        }
Esempio n. 15
0
        public void WordFilesRepository_Should_Extract_Question_Table_From_Docx()
        {
            var wordDocRepo = new WordFilesRepository();

            var rootPath = IntegrationTestsHelper.GetFullResourcePath("integration-test-question-table.docx");

            var doc = wordDocRepo.GetDocument(rootPath);

            doc.Should().NotBeNull();
            doc.Tables.Should().HaveCount(1);
            doc.Tables[0].Question.Should().Be("Test question");
            doc.Tables[0].Answers[0].Should().Be("Test answer 1");
            doc.Tables[0].Answers[1].Should().Be("Test answer 2");
            doc.Tables[0].Answers[2].Should().Be("Test answer 3");
        }
        public void HundredOf2mbPacket_transmitsViaTcp_concurent()
        {
            var origin = TntBuilder
                         .UseContract <ISingleMessageContract <Company>, SingleMessageContract <Company> >()
                         .SetMaxAnsDelay(5 * 60 * 1000);
            var proxy = TntBuilder
                        .UseContract <ISingleMessageContract <Company> >()
                        .SetMaxAnsDelay(5 * 60 * 1000);

            using (var tcpPair = new TcpConnectionPair
                                 <ISingleMessageContract <Company>,
                                  ISingleMessageContract <Company>,
                                  SingleMessageContract <Company> >(origin, proxy))
            {
                var receivedList = new List <Company>(200);

                tcpPair.OriginContract.SayCalled
                    += (Sender, received) => receivedList.Add(received);
                tcpPair.ClientChannel.OnDisconnect += (s, err) =>
                {
                    Console.WriteLine("asdasd");
                };
                var company   = IntegrationTestsHelper.CreateCompany(2000);
                int sendCount = 100;

                List <Task> sendTasks = new List <Task>(sendCount);
                for (int i = 0; i < sendCount; i++)
                {
                    sendTasks.Add(new Task(() => tcpPair.ProxyConnection.Contract.Ask(company)));
                }

                foreach (Task task in sendTasks)
                {
                    task.Start();
                }
                if (!Task.WaitAll(sendTasks.ToArray(), 5 * 60 * 1000))
                {
                    Assert.Fail("Test timeout ");
                }


                Assert.AreEqual(sendCount, receivedList.Count);
                foreach (var received in receivedList)
                {
                    received.AssertIsSameTo(company);
                }
            }
        }
        public void LocalOriginSerializationFails_throws()
        {
            var originContractBuilder = IntegrationTestsHelper.GetOriginBuilder()
                                        .UseSerializer(IntegrationTestsHelper.GetThrowsSerializationRuleFor <string>());

            using (var tcpPair = new TcpConnectionPair <ITestContract, ITestContract, TestContractMock>
                                     (originContractBuilder, IntegrationTestsHelper.GetProxyBuilder()))
            {
                //local origin serializer fails
                Assert.Multiple(() =>
                {
                    Assert.Throws <LocalSerializationException>(() => tcpPair.OriginContract.OnSayS("testString"));
                    tcpPair.AssertPairIsDisconnected();
                });
            }
        }
Esempio n. 18
0
 private static void CheckProtobuffEchoTransaction(int itemsSize)
 {
     using (var tcpPair = new TcpConnectionPair
                          <ISingleMessageContract <Company>,
                           ISingleMessageContract <Company>,
                           SingleMessageContract <Company> >())
     {
         EventAwaiter <Company> callAwaiter = new EventAwaiter <Company>();
         tcpPair.OriginContract.SayCalled += callAwaiter.EventRaised;
         var company = IntegrationTestsHelper.CreateCompany(itemsSize);
         tcpPair.ProxyConnection.Contract.Ask(company);
         var received = callAwaiter.WaitOneOrDefault(5000);
         Assert.IsNotNull(received);
         received.AssertIsSameTo(company);
     }
 }
        public void LocalProxyDeserializationFails_throws()
        {
            var proxyContractBuilder = IntegrationTestsHelper
                                       .GetProxyBuilder()
                                       .UseDeserializer(IntegrationTestsHelper.GetThrowsDeserializationRuleFor <string>());

            using (var tcpPair = new TcpConnectionPair <ITestContract, ITestContract, TestContractMock>
                                     (IntegrationTestsHelper.GetOriginBuilder(), proxyContractBuilder))
            {
                //proxy contract uses failed string deserializer, when it accepts answer
                Assert.Multiple(() =>
                {
                    Assert.Throws <LocalSerializationException>(() => tcpPair.ProxyContract.Ask("testString"));
                    tcpPair.AssertPairIsDisconnected();
                });
            }
        }
Esempio n. 20
0
        public async Task CountDocumentsInCollection_NormalCase()
        {
            await this.InitializeDocumentsAsync();

            int partitionKeyRangeCount = await IntegrationTestsHelper.GetPartitionCount(this.MonitoredCollectionInfo);

            int openedCount = 0, closedCount = 0, processedCount = 0;
            var allDocsProcessed = new ManualResetEvent(false);

            var observerFactory = new TestObserverFactory(
                context => { Interlocked.Increment(ref openedCount); return(Task.CompletedTask); },
                (context, reason) => { Interlocked.Increment(ref closedCount); return(Task.CompletedTask); },
                (ChangeFeedObserverContext context, IReadOnlyList <Document> docs) =>
            {
                int newCount = Interlocked.Add(ref processedCount, docs.Count);
                if (newCount == documentCount)
                {
                    allDocsProcessed.Set();
                }
                return(Task.CompletedTask);
            });

            var host = new ChangeFeedEventHost(
                Guid.NewGuid().ToString(),
                this.MonitoredCollectionInfo,
                this.LeaseCollectionInfo,
                new ChangeFeedOptions {
                StartFromBeginning = true
            },
                new ChangeFeedHostOptions());
            await host.RegisterObserverFactoryAsync(observerFactory);

            allDocsProcessed.WaitOne(changeWaitTimeout + changeWaitTimeout);

            try
            {
                Assert.True(partitionKeyRangeCount == openedCount, "Wrong openedCount");
                Assert.True(documentCount == processedCount, $"Wrong processedCount {documentCount} {processedCount}");
            }
            finally
            {
                await host.UnregisterObserversAsync();
            }

            Assert.True(partitionKeyRangeCount == closedCount, "Wrong closedCount");
        }
Esempio n. 21
0
        public void WordFilesRepository_Should_Extract_Cheatsheet_Table_From_Docx()
        {
            var wordDocRepo = new WordFilesRepository();

            var rootPath = IntegrationTestsHelper.GetFullResourcePath("integration-test-cheatsheet-table.docx");

            var doc = wordDocRepo.GetDocument(rootPath);

            doc.Should().NotBeNull();
            doc.Tables.Should().HaveCount(3);
            doc.Tables[0].Question.Should().Be(@"Test question 1/3");
            doc.Tables[0].Answer.Should().Be(@"cmd answer –demo1");
            doc.Tables[1].Question.Should().Be(@"Test question 2/3");
            doc.Tables[1].Answer.Should().Be(@"cmd answer –demo2");
            doc.Tables[2].Question.Should().Be(@"Test question 3/3");
            doc.Tables[2].Answer.Should().Be(@"cmd answer –demo3");
        }
        public void RemoteOriginSeserializationFails_throws()
        {
            var proxyContractBuilder = IntegrationTestsHelper
                                       .GetProxyBuilder()
                                       .UseSerializer(IntegrationTestsHelper.GetThrowsSerializationRuleFor <string>());

            using (var tcpPair = new TcpConnectionPair <ITestContract, ITestContract, TestContractMock>
                                     (IntegrationTestsHelper.GetOriginBuilder(), proxyContractBuilder))
            {
                //proxy contract uses failed string serializer, when it returns answer
                Assert.Multiple(() =>
                {
                    Assert.Throws <RemoteSerializationException>(() => tcpPair.OriginContract.OnAskS("testString"));
                    tcpPair.AssertPairIsDisconnected();
                });
            }
        }
        private static async Task <DocumentCollectionInfo> TestClassInitializeAsync(IntegrationTest test, string monitoredCollectionName)
        {
            Debug.Assert(test != null);
            Debug.Assert(monitoredCollectionName != null);

            DocumentCollectionInfo leaseCollectionInfo;

            IntegrationTestsHelper.GetConfigurationSettings(
                out test.ClassData.monitoredCollectionInfo,
                out leaseCollectionInfo,
                out monitoredOfferThroughput,
                out leaseOfferThroughput);

            test.ClassData.monitoredCollectionInfo.CollectionName = monitoredCollectionName;

            var monitoredCollection = new DocumentCollection
            {
                Id = test.ClassData.monitoredCollectionInfo.CollectionName,
            };

            if (test.ClassData.isPartitionedCollection)
            {
                monitoredCollection.PartitionKey = new PartitionKeyDefinition {
                    Paths = new Collection <string> {
                        "/id"
                    }
                };
            }
            else
            {
                if (monitoredOfferThroughput > 10000)
                {
                    monitoredOfferThroughput = 10000;
                }
            }

            using (var client = new DocumentClient(test.ClassData.monitoredCollectionInfo.Uri, test.ClassData.monitoredCollectionInfo.MasterKey, test.ClassData.monitoredCollectionInfo.ConnectionPolicy))
            {
                await IntegrationTestsHelper.CreateDocumentCollectionAsync(client, test.ClassData.monitoredCollectionInfo.DatabaseName, monitoredCollection, monitoredOfferThroughput);
            }

            test.FinishTestClassInitializeAsync().Wait();

            return(leaseCollectionInfo);
        }
        private async Task CreateMonitoredCollectionAsync(string monitoredCollectionName)
        {
            Debug.Assert(monitoredCollectionName != null);

            IntegrationTestsHelper.GetConfigurationSettings(
                out DocumentCollectionInfo baseMonitoredCollectionInfo,
                out DocumentCollectionInfo baseLeaseCollectionInfo,
                out monitoredOfferThroughput,
                out leaseOfferThroughput);

            this.MonitoredCollectionInfo = baseMonitoredCollectionInfo;
            this.LeaseCollectionInfo     = baseLeaseCollectionInfo;

            this.MonitoredCollectionInfo.CollectionName = monitoredCollectionName;

            var monitoredCollection = new DocumentCollection
            {
                Id = this.MonitoredCollectionInfo.CollectionName,
            };

            if (this.IsPartitionedMonitoredCollection)
            {
                monitoredCollection.PartitionKey = new PartitionKeyDefinition {
                    Paths = { "/id" }
                };
            }
            else
            {
                if (monitoredOfferThroughput > 10000)
                {
                    monitoredOfferThroughput = 10000;
                }
            }

            using (var client = new DocumentClient(this.MonitoredCollectionInfo.Uri, this.MonitoredCollectionInfo.MasterKey, this.MonitoredCollectionInfo.ConnectionPolicy))
            {
                await IntegrationTestsHelper.CreateDocumentCollectionAsync(client, this.MonitoredCollectionInfo.DatabaseName, monitoredCollection, monitoredOfferThroughput);
            }
        }
Esempio n. 25
0
        public void RunMockup()
        {
            var gmThread = CreateGmThread();
            var csThread = IntegrationTestsHelper.CreateCsThread();

            csThread.Start();
            gmThread.Start();

            Thread.Sleep(3000); //time for connecting gm with cs

            var agents = IntegrationTestsHelper.CreateAgents(agentsInTeam);

            foreach (var agent in agents)
            {
                var agentThread = new Thread(RunAgent);
                agentThread.IsBackground = true; //background threads for termination at test exit
                agentThread.Start(agent);
            }

            gmThread.Join();
            Environment.Exit(Environment.ExitCode); //second nail for preventing thread garbage
        }
Esempio n. 26
0
        public async Task StopAtFullSpeed()
        {
            int partitionKeyRangeCount = await IntegrationTestsHelper.GetPartitionCount(this.MonitoredCollectionInfo);

            int openedCount = 0, closedCount = 0, processedCount = 0;
            var quarterDocsProcessed = new ManualResetEvent(false);

            var observerFactory = new TestObserverFactory(
                context => { Interlocked.Increment(ref openedCount); return(Task.CompletedTask); },
                (context, reason) => { Interlocked.Increment(ref closedCount); return(Task.CompletedTask); },
                (ChangeFeedObserverContext context, IReadOnlyList <Document> docs) =>
            {
                int newCount = Interlocked.Add(ref processedCount, docs.Count);
                if (newCount >= documentCount / 4)
                {
                    quarterDocsProcessed.Set();
                }
                return(Task.CompletedTask);
            });

            var host = new ChangeFeedEventHost(
                Guid.NewGuid().ToString(),
                this.MonitoredCollectionInfo,
                this.LeaseCollectionInfo,
                new ChangeFeedOptions {
                StartFromBeginning = true, MaxItemCount = 2
            },
                new ChangeFeedHostOptions());
            await host.RegisterObserverFactoryAsync(observerFactory);

            quarterDocsProcessed.WaitOne(changeWaitTimeout + changeWaitTimeout);

            await host.UnregisterObserversAsync();

            Assert.True(partitionKeyRangeCount == openedCount, "Wrong closedCount");
            Assert.True(partitionKeyRangeCount == closedCount, "Wrong closedCount");
        }
        public async Task CountPendingDocuments()
        {
            int documentCount  = 1;
            int partitionCount = await IntegrationTestsHelper.GetPartitionCount(this.MonitoredCollectionInfo);

            int openedCount = 0, processedCount = 0;
            var allObserversStarted = new ManualResetEvent(false);
            var allDocsProcessed    = new ManualResetEvent(false);

            var observerFactory = new TestObserverFactory(
                context =>
            {
                int newCount = Interlocked.Increment(ref openedCount);
                if (newCount == partitionCount)
                {
                    allObserversStarted.Set();
                }
                return(Task.CompletedTask);
            },
                null,
                (ChangeFeedObserverContext context, IReadOnlyList <Document> docs) =>
            {
                int newCount = Interlocked.Add(ref processedCount, docs.Count);
                if (newCount == documentCount)
                {
                    allDocsProcessed.Set();
                }
                return(Task.CompletedTask);
            });

            var hostName = Guid.NewGuid().ToString();

            var host = new ChangeFeedEventHost(
                hostName,
                this.MonitoredCollectionInfo,
                this.LeaseCollectionInfo,
                new ChangeFeedOptions {
                StartFromBeginning = false
            },
                new ChangeFeedHostOptions());

            // Initialize leases
            await host.RegisterObserverFactoryAsync(observerFactory);

            // Verify that 0 is returned on empty collection
            long estimation = await host.GetEstimatedRemainingWork();

            Assert.Equal(0, estimation);

            using (var client = new DocumentClient(this.MonitoredCollectionInfo.Uri, this.MonitoredCollectionInfo.MasterKey, this.MonitoredCollectionInfo.ConnectionPolicy))
            {
                await IntegrationTestsHelper.CreateDocumentsAsync(
                    client,
                    UriFactory.CreateDocumentCollectionUri(this.MonitoredCollectionInfo.DatabaseName, this.MonitoredCollectionInfo.CollectionName),
                    1);

                var isStartOk = allObserversStarted.WaitOne(IntegrationTest.changeWaitTimeout + IntegrationTest.changeWaitTimeout);
                Assert.True(isStartOk, "Timed out waiting for observer to start");

                allDocsProcessed.WaitOne(IntegrationTest.changeWaitTimeout);

                // Halt the processor temporarily
                await host.UnregisterObserversAsync();

                estimation = await host.GetEstimatedRemainingWork();

                Assert.Equal(0, estimation);

                await IntegrationTestsHelper.CreateDocumentsAsync(
                    client,
                    UriFactory.CreateDocumentCollectionUri(this.MonitoredCollectionInfo.DatabaseName, this.MonitoredCollectionInfo.CollectionName),
                    1);

                estimation = await host.GetEstimatedRemainingWork();

                Assert.Equal(1, estimation);

                await IntegrationTestsHelper.CreateDocumentsAsync(
                    client,
                    UriFactory.CreateDocumentCollectionUri(this.MonitoredCollectionInfo.DatabaseName, this.MonitoredCollectionInfo.CollectionName),
                    10);

                estimation = await host.GetEstimatedRemainingWork();

                Assert.Equal(11, estimation);

                // Create a new host to process pending changes
                var newHost = new ChangeFeedEventHost(
                    hostName,
                    this.MonitoredCollectionInfo,
                    this.LeaseCollectionInfo,
                    new ChangeFeedOptions {
                    StartFromBeginning = false
                },
                    new ChangeFeedHostOptions());

                openedCount    = 0;
                processedCount = 0;
                allObserversStarted.Reset();
                allDocsProcessed.Reset();

                await newHost.RegisterObserverFactoryAsync(observerFactory);

                isStartOk = allObserversStarted.WaitOne(IntegrationTest.changeWaitTimeout + IntegrationTest.changeWaitTimeout);
                Assert.True(isStartOk, "Timed out waiting for observer to start");

                allDocsProcessed.WaitOne(IntegrationTest.changeWaitTimeout);

                try
                {
                    estimation = await newHost.GetEstimatedRemainingWork();

                    Assert.Equal(0, estimation);
                }
                finally
                {
                    await newHost.UnregisterObserversAsync();
                }
            }
        }
Esempio n. 28
0
        public async Task Schema_OnV2MigrationMaintainLeaseToken()
        {
            const int batchSize      = 10;
            int       partitionCount = await IntegrationTestsHelper.GetPartitionCount(this.MonitoredCollectionInfo);

            int openedCount = 0;
            ManualResetEvent    allObserversStarted         = new ManualResetEvent(false);
            List <int>          expectedIds                 = Enumerable.Range(0, batchSize * 2).ToList();
            ManualResetEvent    firstSetOfResultsProcessed  = new ManualResetEvent(false);
            ManualResetEvent    secondSetOfResultsProcessed = new ManualResetEvent(false);
            List <int>          receivedIds                 = new List <int>();
            TestObserverFactory observerFactory             = new TestObserverFactory(
                context =>
            {
                int newCount = Interlocked.Increment(ref openedCount);
                if (newCount == partitionCount)
                {
                    allObserversStarted.Set();
                }
                return(Task.CompletedTask);
            },
                (FeedProcessing.IChangeFeedObserverContext context, IReadOnlyList <Document> docs) =>
            {
                foreach (Document doc in docs)
                {
                    receivedIds.Add(int.Parse(doc.Id));
                }

                if (receivedIds.Count == batchSize)
                {
                    firstSetOfResultsProcessed.Set();
                }

                if (receivedIds.Count == batchSize * 2)
                {
                    secondSetOfResultsProcessed.Set();
                }

                return(Task.CompletedTask);
            });

            IChangeFeedProcessor changeFeedProcessorBuilder = await new ChangeFeedProcessorBuilder()
                                                              .WithObserverFactory(observerFactory)
                                                              .WithHostName("smoke_test")
                                                              .WithFeedCollection(this.MonitoredCollectionInfo)
                                                              .WithLeaseCollection(this.LeaseCollectionInfo)
                                                              .BuildAsync();

            await changeFeedProcessorBuilder.StartAsync();

            await this.WaitUntilLeaseStoreIsInitializedAsync(new CancellationTokenSource(5000).Token);

            // Inserting some documents
            using (DocumentClient client = new DocumentClient(this.MonitoredCollectionInfo.Uri, this.MonitoredCollectionInfo.MasterKey, this.MonitoredCollectionInfo.ConnectionPolicy))
            {
                Uri collectionUri = UriFactory.CreateDocumentCollectionUri(this.MonitoredCollectionInfo.DatabaseName, this.MonitoredCollectionInfo.CollectionName);

                foreach (int id in expectedIds.Take(10))
                {
                    await client.CreateDocumentAsync(collectionUri, new { id = id.ToString() });
                }
            }

            Assert.True(firstSetOfResultsProcessed.WaitOne(IntegrationTest.changeWaitTimeout), "Timed out waiting for first set of items to be received.");

            await changeFeedProcessorBuilder.StopAsync();

            // At this point we have leases for V2, so we will simulate V3 by manually adding LeaseToken and removing PartitionId
            using (DocumentClient client = new DocumentClient(this.LeaseCollectionInfo.Uri, this.LeaseCollectionInfo.MasterKey, this.LeaseCollectionInfo.ConnectionPolicy))
            {
                Uri collectionUri = UriFactory.CreateDocumentCollectionUri(this.LeaseCollectionInfo.DatabaseName, this.LeaseCollectionInfo.CollectionName);

                IDocumentQuery <JObject> query = client.CreateDocumentQuery <JObject>(collectionUri, "SELECT * FROM c").AsDocumentQuery();
                while (query.HasMoreResults)
                {
                    foreach (JObject lease in await query.ExecuteNextAsync())
                    {
                        string leaseId = lease.Value <string>("id");
                        if (leaseId.Contains(".info"))
                        {
                            // These are the store initialization marks
                            continue;
                        }

                        // create the LeaseToken property
                        lease.Add("LeaseToken", lease.Value <string>("PartitionId"));

                        lease.Remove("PartitionId");

                        await client.UpsertDocumentAsync(collectionUri, lease);
                    }
                }
            }

            // Now all leases are V3 leases, start another processor that should migrate to V2 schema and maintain LeaseToken for compatibility
            openedCount = 0;
            allObserversStarted.Reset();
            changeFeedProcessorBuilder = await new ChangeFeedProcessorBuilder()
                                         .WithObserverFactory(observerFactory)
                                         .WithHostName("smoke_test")
                                         .WithFeedCollection(this.MonitoredCollectionInfo)
                                         .WithLeaseCollection(this.LeaseCollectionInfo)
                                         .BuildAsync();

            await changeFeedProcessorBuilder.StartAsync();

            Assert.True(allObserversStarted.WaitOne(IntegrationTest.changeWaitTimeout + IntegrationTest.changeWaitTimeout), "Timed out waiting for observres to start");
            // Create the rest of the documents
            using (DocumentClient client = new DocumentClient(this.MonitoredCollectionInfo.Uri, this.MonitoredCollectionInfo.MasterKey, this.MonitoredCollectionInfo.ConnectionPolicy))
            {
                Uri collectionUri = UriFactory.CreateDocumentCollectionUri(this.MonitoredCollectionInfo.DatabaseName, this.MonitoredCollectionInfo.CollectionName);

                foreach (int id in expectedIds.TakeLast(10))
                {
                    await client.CreateDocumentAsync(collectionUri, new { id = id.ToString() });
                }
            }

            Assert.True(secondSetOfResultsProcessed.WaitOne(IntegrationTest.changeWaitTimeout), "Timed out waiting for second set of items to be received.");
            await changeFeedProcessorBuilder.StopAsync();

            // Verify we processed all items (including when using the V3 leases)
            Assert.True(!expectedIds.Except(receivedIds).Any() && expectedIds.Count == expectedIds.Count);


            // Verify the after-migration leases have both PartitionId and LeaseToken with the same value
            using (DocumentClient client = new DocumentClient(this.LeaseCollectionInfo.Uri, this.LeaseCollectionInfo.MasterKey, this.LeaseCollectionInfo.ConnectionPolicy))
            {
                Uri collectionUri = UriFactory.CreateDocumentCollectionUri(this.LeaseCollectionInfo.DatabaseName, this.LeaseCollectionInfo.CollectionName);

                IDocumentQuery <JObject> query = client.CreateDocumentQuery <JObject>(collectionUri, "SELECT * FROM c").AsDocumentQuery();
                while (query.HasMoreResults)
                {
                    foreach (JObject lease in await query.ExecuteNextAsync())
                    {
                        string leaseId = lease.Value <string>("id");
                        if (leaseId.Contains(".info"))
                        {
                            // These are the store initialization marks
                            continue;
                        }

                        Assert.NotNull(lease.Value <string>("PartitionId"));
                        Assert.Null(lease.Value <string>("LeaseToken"));
                    }
                }
            }
        }
        public async Task TestStartTime()
        {
            var collectionUri = UriFactory.CreateDocumentCollectionUri(this.MonitoredCollectionInfo.DatabaseName, this.MonitoredCollectionInfo.CollectionName);

            using (var client = new DocumentClient(this.MonitoredCollectionInfo.Uri, this.MonitoredCollectionInfo.MasterKey, this.MonitoredCollectionInfo.ConnectionPolicy))
            {
                await client.CreateDocumentAsync(collectionUri, JsonConvert.DeserializeObject("{\"id\": \"doc1\"}"));

                // In worst case (long transaction, heavy load, the atomicity of StartTime is 5 sec).
                // For this case (different transactions) it's OK to wait timestamp precision time.
                await Task.Delay(TimeSpan.FromSeconds(1));

                DateTime timeInBeweeen = DateTime.Now;
                await Task.Delay(TimeSpan.FromSeconds(1));

                await client.CreateDocumentAsync(collectionUri, JsonConvert.DeserializeObject("{\"id\": \"doc2\"}"));

                int partitionCount = await IntegrationTestsHelper.GetPartitionCount(this.MonitoredCollectionInfo);

                var allDocsProcessed = new ManualResetEvent(false);

                var processedDocs   = new List <Document>();
                var observerFactory = new TestObserverFactory(
                    null,
                    null,
                    (context, docs) =>
                {
                    processedDocs.AddRange(docs);
                    foreach (var doc in docs)
                    {
                        if (doc.Id == "doc2")
                        {
                            allDocsProcessed.Set();
                        }
                    }
                    return(Task.CompletedTask);
                });

                var host = new ChangeFeedEventHost(
                    Guid.NewGuid().ToString(),
                    this.MonitoredCollectionInfo,
                    this.LeaseCollectionInfo,
                    new ChangeFeedOptions {
                    StartTime = timeInBeweeen
                },
                    new ChangeFeedHostOptions());
                await host.RegisterObserverFactoryAsync(observerFactory);

                var isStartOk = allDocsProcessed.WaitOne(IntegrationTest.changeWaitTimeout + IntegrationTest.changeWaitTimeout);

                try
                {
                    Assert.True(isStartOk, "Timed out waiting for docs to process");
                    Assert.True(1 == processedDocs.Count, "Wrong processed count");
                    Assert.True("doc2" == processedDocs[0].Id, "Wrong doc.id");
                }
                finally
                {
                    await host.UnregisterObserversAsync();
                }
            }
        }
        public async Task CountAddedDocuments()
        {
            int partitionCount = await IntegrationTestsHelper.GetPartitionCount(this.MonitoredCollectionInfo);

            int openedCount = 0, processedCount = 0;
            var allObserversStarted = new ManualResetEvent(false);
            var allDocsProcessed    = new ManualResetEvent(false);

            var observerFactory = new TestObserverFactory(
                context =>
            {
                int newCount = Interlocked.Increment(ref openedCount);
                if (newCount == partitionCount)
                {
                    allObserversStarted.Set();
                }
                return(Task.CompletedTask);
            },
                null,
                (ChangeFeedObserverContext context, IReadOnlyList <Document> docs) =>
            {
                int newCount = Interlocked.Add(ref processedCount, docs.Count);
                if (newCount == documentCount)
                {
                    allDocsProcessed.Set();
                }
                return(Task.CompletedTask);
            });

            var host = new ChangeFeedEventHost(
                Guid.NewGuid().ToString(),
                this.MonitoredCollectionInfo,
                this.LeaseCollectionInfo,
                new ChangeFeedOptions {
                StartFromBeginning = false
            },
                new ChangeFeedHostOptions());
            await host.RegisterObserverFactoryAsync(observerFactory);

            var isStartOk = allObserversStarted.WaitOne(IntegrationTest.changeWaitTimeout + IntegrationTest.changeWaitTimeout);

            Assert.True(isStartOk, "Timed out waiting for observres to start");

            using (var client = new DocumentClient(this.MonitoredCollectionInfo.Uri, this.MonitoredCollectionInfo.MasterKey, this.MonitoredCollectionInfo.ConnectionPolicy))
            {
                await IntegrationTestsHelper.CreateDocumentsAsync(
                    client,
                    UriFactory.CreateDocumentCollectionUri(this.MonitoredCollectionInfo.DatabaseName, this.MonitoredCollectionInfo.CollectionName),
                    documentCount);
            }

            allDocsProcessed.WaitOne(IntegrationTest.changeWaitTimeout);

            try
            {
                Assert.True(documentCount == processedCount, "Wrong processedCount");
            }
            finally
            {
                await host.UnregisterObserversAsync();
            }
        }