public async Task NotInRehabWithDisabledIndexes1() { var(node, leader) = await CreateRaftCluster(3, watcherCluster : true); var database = GetDatabaseName(); await CreateDatabaseInClusterInner(new DatabaseRecord(database), 3, leader.WebUrl, null); using (var store = new DocumentStore { Database = database, Urls = new[] { leader.WebUrl } }.Initialize()) { var documentDatabase = await Servers[2].ServerStore.DatabasesLandlord.TryGetOrCreateResourceStore(database); var result = store.Maintenance.Send(new PutIndexesOperation(new[] { new IndexDefinition { Maps = { "from user in docs.Users select new { user.Name }" }, Name = "MyIndex" } })); var indexResult = result[0]; await Cluster.WaitForRaftIndexToBeAppliedInClusterAsync(indexResult.RaftCommandIndex, TimeSpan.FromSeconds(15)); foreach (var server in Servers) { documentDatabase = await server.ServerStore.DatabasesLandlord.TryGetOrCreateResourceStore(database); await RollingIndexesClusterTests.WaitForRollingIndex(database, "MyIndex", server); var index = documentDatabase.IndexStore.GetIndex("MyIndex"); index.SetState(IndexState.Disabled); } var record = await store.Maintenance.Server.SendAsync(new GetDatabaseRecordOperation(store.Database)); record.Topology.Members.Remove(Servers[2].ServerStore.NodeTag); record.Topology.Rehabs.Add(Servers[2].ServerStore.NodeTag); await store.Maintenance.Server.SendAsync(new UpdateDatabaseOperation(record, record.Etag)); var rehabs = await WaitForValueAsync(async() => await GetRehabCount(store, store.Database), 1); Assert.Equal(1, rehabs); var val = await WaitForValueAsync(async() => await GetMembersCount(store, database), 2); Assert.Equal(2, val); val = await WaitForValueAsync(async() => await GetMembersCount(store, store.Database), 3); Assert.Equal(3, val); rehabs = await WaitForValueAsync(async() => await GetRehabCount(store, store.Database), 0); Assert.Equal(0, rehabs); } }
public async Task StayInRehabWithErrorIndexes2() { var(node, leader) = await CreateRaftCluster(3, watcherCluster : true); var database = GetDatabaseName(); await CreateDatabaseInClusterInner(new DatabaseRecord(database), 3, leader.WebUrl, null); using (var store = new DocumentStore { Database = database, Urls = new[] { leader.WebUrl } }.Initialize()) { var documentDatabase = await Servers[2].ServerStore.DatabasesLandlord.TryGetOrCreateResourceStore(database); var result = store.Maintenance.Send(new PutIndexesOperation(new[] { new IndexDefinition { Maps = { "from user in docs.Users select new { user.Name }" }, Name = "MyIndex" } })); var indexResult = result[0]; await Cluster.WaitForRaftIndexToBeAppliedInClusterAsync(indexResult.RaftCommandIndex, TimeSpan.FromSeconds(15)); await RollingIndexesClusterTests.WaitForRollingIndex(database, "MyIndex", Servers[2]); var index = documentDatabase.IndexStore.GetIndex("MyIndex"); index.SetState(IndexState.Error); using (var session = store.OpenSession()) { session.Store(new User() { Name = "Toli" }, "user/1"); session.SaveChanges(); } using (var context = QueryOperationContext.Allocate(documentDatabase, index)) using (context.OpenReadTransaction()) { var state = index.GetIndexingState(context); Assert.Equal(0, state.LastProcessedEtag); } var record = await store.Maintenance.Server.SendAsync(new GetDatabaseRecordOperation(store.Database)); record.Topology.Members.Remove(Servers[2].ServerStore.NodeTag); record.Topology.Rehabs.Add(Servers[2].ServerStore.NodeTag); await store.Maintenance.Server.SendAsync(new UpdateDatabaseOperation(record, record.Etag)); var rehabs = await WaitForValueAsync(async() => await GetRehabCount(store, store.Database), 1); Assert.Equal(1, rehabs); var val = await WaitForValueAsync(async() => await GetMembersCount(store, database), 2); Assert.Equal(2, val); val = await WaitForValueAsync(async() => await GetMembersCount(store, store.Database), 3); Assert.Equal(2, val); } }
public async Task NotInRehabWithDisabledIndexes3() { var(node, leader) = await CreateRaftCluster(3, watcherCluster : true); var database = GetDatabaseName(); await CreateDatabaseInClusterInner(new DatabaseRecord(database), 3, leader.WebUrl, null); using (var store = new DocumentStore { Database = database, Urls = new[] { leader.WebUrl } }.Initialize()) { var documentDatabase = await Servers[2].ServerStore.DatabasesLandlord.TryGetOrCreateResourceStore(database); var result = store.Maintenance.Send(new PutIndexesOperation(new[] { new IndexDefinition { Maps = { "from user in docs.Users select new { user.Name }" }, Name = "MyIndex" } })); var indexResult = result[0]; await Cluster.WaitForRaftIndexToBeAppliedInClusterAsync(indexResult.RaftCommandIndex, TimeSpan.FromSeconds(15)); await RollingIndexesClusterTests.WaitForRollingIndex(database, "MyIndex", Servers[2]); var index = documentDatabase.IndexStore.GetIndex("MyIndex"); index.SetState(IndexState.Error); using (var session = store.OpenSession()) { session.Store(new User() { Name = "Toli" }, "user/1"); session.SaveChanges(); } index.SetState(IndexState.Disabled); using (var context = QueryOperationContext.Allocate(documentDatabase, index)) using (context.OpenReadTransaction()) { var state = index.GetIndexingState(context); Assert.Equal(0, state.LastProcessedEtag); } var record = await store.Maintenance.Server.SendAsync(new GetDatabaseRecordOperation(store.Database)); record.Topology.Members.Remove(Servers[2].ServerStore.NodeTag); record.Topology.Rehabs.Add(Servers[2].ServerStore.NodeTag); await store.Maintenance.Server.SendAsync(new UpdateDatabaseOperation(record, record.Etag)); await WaitAndAssertForValueAsync(async() => await RavenDB_15588.GetMembersAndRehabsCount(store), expectedVal : (MembersCount : 2, RehabsCount : 1)); // assert that Servers[2] is promoted back to Member var expectedVal = (MembersCount : 3, RehabsCount : 0); var val = await WaitForPredicateAsync(async() => await RavenDB_15588.GetMembersAndRehabsCount(store), expectedVal : expectedVal); Assert.True(val.Equals(expectedVal), await GetDecisionsForDatabase( new StringBuilder("Failed on asserting Members and Rehabs count.") .AppendLine($"Expected {expectedVal}, got : {val}"))); } }
public async Task CanPassNodeTagToRestorePatchOperation() { var clusterSize = 3; var databaseName = GetDatabaseName(); (List <RavenServer> Nodes, RavenServer Leader)cluster = await CreateRaftCluster(clusterSize, shouldRunInMemory : false); var myNodesList = new List <string>(); using (var store = new DocumentStore { Urls = new[] { cluster.Leader.WebUrl }, Database = databaseName, }.Initialize()) { var doc = new DatabaseRecord(databaseName); var databaseResult = await store.Maintenance.Server.SendAsync(new CreateDatabaseOperation(doc, clusterSize)); myNodesList.AddRange(databaseResult.Topology.AllNodes); var result = store.Maintenance.Send(new PutIndexesOperation(new[] { new IndexDefinition { Maps = { "from doc in docs.Items select new { doc.Name }" }, Name = "MyIndex" } })); var indexResult = result[0]; await Cluster.WaitForRaftIndexToBeAppliedOnClusterNodesAsync(indexResult.RaftCommandIndex, cluster.Nodes); using (var commands = store.Commands()) { await commands.PutAsync("items/1", null, new { Name = "testname" }, new Dictionary <string, object> { { Constants.Documents.Metadata.Collection, "Items" } }); await WaitForDocumentInClusterAsync <dynamic>(store.GetRequestExecutor().Topology.Nodes, "items/1", predicate : null, TimeSpan.FromSeconds(15)); await RollingIndexesClusterTests.WaitForRollingIndex(databaseName, "MyIndex", cluster.Nodes); WaitForIndexingInTheCluster(store, timeout: TimeSpan.FromSeconds(60)); Operation operation = await store.Operations.SendAsync(new PatchByQueryOperation(new IndexQuery { Query = "FROM INDEX 'MyIndex' UPDATE { this.NewName = 'NewValue'; } " })); var opStatus = await store.Maintenance.SendAsync(new GetOperationStateOperation(operation.Id)); Assert.NotNull(opStatus); foreach (var node in myNodesList) { var op = await store.Maintenance.SendAsync(new GetOperationStateOperation(operation.Id, node)); if (node == operation.NodeTag) { Assert.NotNull(op); } else { Assert.Null(op); } } await operation.WaitForCompletionAsync(TimeSpan.FromSeconds(60)); dynamic document = await commands.GetAsync("items/1"); Assert.Equal("NewValue", document.NewName.ToString()); } } }