private List<ReplicationTopologySourceNode> HandleSources(IEnumerable<RavenJToken> sources, ReplicationTopologyRootNode root)
		{
			var nodes = new List<ReplicationTopologySourceNode>();
			foreach (var sourceAsJson in sources.Cast<RavenJObject>())
			{
				SourceReplicationInformation source = null;
				try
				{
					source = sourceAsJson.JsonDeserialization<SourceReplicationInformation>();
				}
				catch (Exception)
				{
					root.Errors.Add(string.Format("Could not deserialize source node."));
				}

				var node = HandleSource(source);
				nodes.Add(node);
			}

			return nodes;
		}
		public ReplicationTopologyRootNode Discover()
		{
			var nextStart = 0;

			var root = new ReplicationTopologyRootNode(database.ServerUrl, database.TransactionalStorage.Id);

			if (ttl <= 0)
				return root;

			var destinations = database.Documents.Get(Constants.RavenReplicationDestinations, null);
			var sources = database.Documents.GetDocumentsWithIdStartingWith(Constants.RavenReplicationSourcesBasePath, null, null, 0, int.MaxValue, database.WorkContext.CancellationToken, ref nextStart);

            if (@from.Contains(database.ServerUrl) == false)
            {
                @from.Add(database.ServerUrl);
            }

			root.Destinations = HandleDestinations(destinations, root);
			root.Sources = HandleSources(sources, root);

			return root;
		}
	    private bool TryGetSchema(string serverUrl, RavenConnectionStringOptions connectionStringOptions, out ReplicationTopologyRootNode rootNode, out string error)
		{
			var url = string.Format("{0}/admin/replication/topology/discover?&ttl={1}", serverUrl, ttl - 1);

			try
			{
				var request = requestFactory.Create(url, "POST", connectionStringOptions);
                request.Write(from);

				error = null;
				rootNode = request.ExecuteRequest<ReplicationTopologyRootNode>();

			    var visitedNodes = new HashSet<string>();
			    FindVisitedNodes(rootNode, visitedNodes);
                foreach (var visitedNode in visitedNodes)
                {
                    if (@from.Contains(visitedNode) == false)
                    {
                        @from.Add(visitedNode);
                    }
                }
				return true;
			}
			catch (Exception e)
			{
				error = e.Message;
				rootNode = null;
				return false;
			}
		}
		private List<ReplicationTopologyDestinationNode> HandleDestinations(JsonDocument destinationsAsJson, ReplicationTopologyRootNode root)
		{
			var nodes = new List<ReplicationTopologyDestinationNode>();

			if (destinationsAsJson == null)
				return nodes;

			ReplicationDocument destinations;
			try
			{
				destinations = destinationsAsJson.DataAsJson.JsonDeserialization<ReplicationDocument>();
			}
			catch (Exception)
			{
				root.Errors.Add(string.Format("Could not deserialize '{0}'.", Constants.RavenReplicationDestinations));

				return nodes;
			}

			nodes.AddRange(destinations.Destinations.Select(HandleDestination));

			return nodes;
		}