public void SendLastQueried() { if (Database.Disposed) { return; } try { using (CultureHelper.EnsureInvariantCulture()) { var relevantIndexLastQueries = new Dictionary <string, DateTime>(); var relevantIndexes = Database.Statistics.Indexes.Where(indexStats => indexStats.IsInvalidIndex == false && indexStats.Priority != IndexingPriority.Error && indexStats.Priority != IndexingPriority.Disabled && indexStats.LastQueryTimestamp.HasValue); foreach (var relevantIndex in relevantIndexes) { relevantIndexLastQueries[relevantIndex.Name] = relevantIndex.LastQueryTimestamp.GetValueOrDefault(); } if (relevantIndexLastQueries.Count == 0) { return; } var destinations = GetReplicationDestinations(x => x.SkipIndexReplication == false); foreach (var destination in destinations) { try { string url = destination.ConnectionStringOptions.Url + "/indexes/last-queried"; var replicationRequest = HttpRavenRequestFactory.Create(url, HttpMethods.Post, destination.ConnectionStringOptions, Replication.GetRequestBuffering(destination)); replicationRequest.Write(RavenJObject.FromObject(relevantIndexLastQueries)); replicationRequest.ExecuteRequest(); } catch (Exception e) { Replication.HandleRequestBufferingErrors(e, destination); Log.WarnException("Could not update last query time of " + destination.ConnectionStringOptions.Url, e); } } } } catch (Exception e) { Log.ErrorException("Failed to send last queried timestamp of indexes", e); } }
private void ReplicateIndexDeletionIfNeeded( List <JsonDocument> indexTombstones, ReplicationStrategy destination, Dictionary <string, int> replicatedIndexTombstones) { if (indexTombstones.Count == 0) { return; } foreach (var tombstone in indexTombstones) { try { int value; //In case the index was recreated under the same name we will increase the destination count for this tombstone //As if we sent the delete request but without actually sending the request, ending with a NOOP and deleting the index tombstone. if (Database.IndexStorage.HasIndex(tombstone.Key)) { replicatedIndexTombstones.TryGetValue(tombstone.Key, out value); replicatedIndexTombstones[tombstone.Key] = value + 1; continue; } var url = string.Format("{0}/indexes/{1}?{2}&{3}", destination.ConnectionStringOptions.Url, Uri.EscapeUriString(tombstone.Key), GetTombstoneVersion(tombstone, IndexDefinitionStorage.IndexVersionKey, Constants.IndexVersion), GetDebugInformation()); var replicationRequest = HttpRavenRequestFactory.Create(url, HttpMethods.Delete, destination.ConnectionStringOptions, Replication.GetRequestBuffering(destination)); replicationRequest.Write(RavenJObject.FromObject(EmptyRequestBody)); replicationRequest.ExecuteRequest(); Log.Info("Replicated index deletion (index name = {0})", tombstone.Key); replicatedIndexTombstones.TryGetValue(tombstone.Key, out value); replicatedIndexTombstones[tombstone.Key] = value + 1; } catch (Exception e) { Replication.HandleRequestBufferingErrors(e, destination); Log.ErrorException(string.Format("Failed to replicate index deletion (index name = {0})", tombstone.Key), e); } } }
private void ReplicateSingleSideBySideIndex(ReplicationStrategy destination, IndexDefinition indexDefinition, IndexDefinition sideBySideIndexDefinition) { var url = $"{destination.ConnectionStringOptions.Url}/replication/side-by-side?{GetDebugInformation()}"; IndexReplaceDocument indexReplaceDocument; try { indexReplaceDocument = Database.Documents.Get(Constants.IndexReplacePrefix + sideBySideIndexDefinition.Name, null).DataAsJson.JsonDeserialization <IndexReplaceDocument>(); } catch (Exception e) { Log.Warn("Cannot get side-by-side index replacement document. Aborting operation. (this exception should not happen and the cause should be investigated)", e); return; } var sideBySideReplicationInfo = new SideBySideReplicationInfo { Index = indexDefinition, SideBySideIndex = sideBySideIndexDefinition, OriginDatabaseId = destination.CurrentDatabaseId, IndexReplaceDocument = indexReplaceDocument }; var replicationRequest = HttpRavenRequestFactory.Create(url, HttpMethod.Post, destination.ConnectionStringOptions, Replication.GetRequestBuffering(destination)); replicationRequest.Write(RavenJObject.FromObject(sideBySideReplicationInfo)); replicationRequest.ExecuteRequest(); }
private void ReplicateSideBySideIndexesMultiPut(ReplicationStrategy destination, List <IndexToAdd> indexes) { var sideBySideIndexes = new SideBySideIndexes { IndexesToAdd = indexes.ToArray() }; var serializedIndexDefinitions = RavenJToken.FromObject(sideBySideIndexes); var url = $"{destination.ConnectionStringOptions.Url}/side-by-side-indexes?{GetDebugInformation()}"; var replicationRequest = HttpRavenRequestFactory.Create(url, HttpMethods.Put, destination.ConnectionStringOptions, Replication.GetRequestBuffering(destination)); replicationRequest.Write(serializedIndexDefinitions); replicationRequest.ExecuteRequest(); }
private void ReplicateTransformerDeletionIfNeeded(List <JsonDocument> transformerTombstones, ReplicationStrategy destination, Dictionary <string, int> replicatedTransformerTombstones) { if (transformerTombstones.Count == 0) { return; } foreach (var tombstone in transformerTombstones) { try { int value; if (Database.Transformers.GetTransformerDefinition(tombstone.Key) != null) //if in the meantime the transformer was recreated under the same name { replicatedTransformerTombstones.TryGetValue(tombstone.Key, out value); replicatedTransformerTombstones[tombstone.Key] = value + 1; continue; } var url = string.Format("{0}/transformers/{1}?{2}", destination.ConnectionStringOptions.Url, Uri.EscapeUriString(tombstone.Key), GetDebugInformation()); var replicationRequest = HttpRavenRequestFactory.Create(url, HttpMethods.Delete, destination.ConnectionStringOptions, Replication.GetRequestBuffering(destination)); replicationRequest.Write(RavenJObject.FromObject(EmptyRequestBody)); replicationRequest.ExecuteRequest(); Log.Info("Replicated transformer deletion (transformer name = {0})", tombstone.Key); replicatedTransformerTombstones.TryGetValue(tombstone.Key, out value); replicatedTransformerTombstones[tombstone.Key] = value + 1; } catch (Exception e) { Replication.HandleRequestBufferingErrors(e, destination); Log.ErrorException(string.Format("Failed to replicate transformer deletion (transformer name = {0})", tombstone.Key), e); } } }
private void ReplicateSingleTransformer(ReplicationStrategy destination, TransformerDefinition definition) { try { var clonedTransformer = definition.Clone(); clonedTransformer.TransfomerId = 0; var url = destination.ConnectionStringOptions.Url + "/transformers/" + Uri.EscapeUriString(definition.Name) + "?" + GetDebugInformation(); var replicationRequest = HttpRavenRequestFactory.Create(url, HttpMethod.Put, destination.ConnectionStringOptions, Replication.GetRequestBuffering(destination)); replicationRequest.Write(RavenJObject.FromObject(clonedTransformer)); replicationRequest.ExecuteRequest(); } catch (Exception e) { Replication.HandleRequestBufferingErrors(e, destination); Log.WarnException("Could not replicate transformer " + definition.Name + " to " + destination.ConnectionStringOptions.Url, e); } }