public async Task<GraphNode> CreateGraphNode(RestoreContext context, LibraryRange libraryRange, Func<string, bool> predicate) { var sw = new Stopwatch(); sw.Start(); var node = new GraphNode { LibraryRange = libraryRange, Item = await FindLibraryCached(context, libraryRange), }; if (node.Item != null) { if (node.LibraryRange.VersionRange != null && node.LibraryRange.VersionRange.VersionFloatBehavior != SemanticVersionFloatBehavior.None) { lock (context.FindLibraryCache) { if (!context.FindLibraryCache.ContainsKey(node.LibraryRange)) { context.FindLibraryCache[node.LibraryRange] = Task.FromResult(node.Item); } } } var tasks = new List<Task<GraphNode>>(); var dependencies = node.Item.Dependencies ?? Enumerable.Empty<LibraryDependency>(); foreach (var dependency in dependencies) { if (predicate(dependency.Name)) { tasks.Add(CreateGraphNode(context, dependency.LibraryRange, ChainPredicate(predicate, node.Item, dependency))); } } while (tasks.Any()) { var task = await Task.WhenAny(tasks); tasks.Remove(task); var dependency = await task; node.Dependencies.Add(dependency); } } return node; }
public async Task<GraphNode> CreateGraphNode(RestoreContext context, LibraryRange libraryRange, Func<string, bool> predicate) { var sw = new Stopwatch(); sw.Start(); var node = new GraphNode { LibraryRange = libraryRange, Item = await FindLibraryCached(context, libraryRange), }; if (node.Item != null) { if (node.LibraryRange.VersionRange != null && node.LibraryRange.VersionRange.VersionFloatBehavior != SemanticVersionFloatBehavior.None) { lock (context.GraphItemCache) { if (!context.GraphItemCache.ContainsKey(node.LibraryRange)) { context.GraphItemCache[node.LibraryRange] = Task.FromResult(node.Item); } } } var tasks = new List<Task<GraphNode>>(); var dependencies = node.Item.Dependencies ?? Enumerable.Empty<LibraryDependency>(); foreach (var dependency in dependencies) { if (predicate(dependency.Name)) { tasks.Add(CreateGraphNode(context, dependency.LibraryRange, ChainPredicate(predicate, node.Item, dependency))); if (context.RuntimeSpecs != null) { foreach (var runtimeSpec in context.RuntimeSpecs) { DependencySpec dependencyMapping; if (runtimeSpec.Dependencies.TryGetValue(dependency.Name, out dependencyMapping)) { foreach (var dependencyImplementation in dependencyMapping.Implementations.Values) { tasks.Add(CreateGraphNode( context, new LibraryRange(dependencyImplementation.Name, frameworkReference: false) { VersionRange = VersionUtility.ParseVersionRange(dependencyImplementation.Version) }, ChainPredicate(predicate, node.Item, dependency))); } break; } } } } } while (tasks.Any()) { var task = await Task.WhenAny(tasks); tasks.Remove(task); var dependency = await task; node.Dependencies.Add(dependency); } } return node; }
private void PrintDependencyGraph(GraphNode root, FrameworkName frameworkName) { // Box Drawing Unicode characters: // http://www.unicode.org/charts/PDF/U2500.pdf const char LIGHT_HORIZONTAL = '\u2500'; const char LIGHT_UP_AND_RIGHT = '\u2514'; const char LIGHT_VERTICAL_AND_RIGHT = '\u251C'; var frameworkSuffix = string.Format(" [{0}]", frameworkName.ToString()); Reports.Verbose.WriteLine(root.Item.Match.Library.ToString() + frameworkSuffix); Func<GraphNode, bool> isValidDependency = d => (d != null && d.Library != null && d.Item != null && d.Item.Match != null); var dependencies = root.Dependencies.Where(isValidDependency).ToList(); var dependencyNum = dependencies.Count; for (int i = 0; i < dependencyNum; i++) { var branchChar = LIGHT_VERTICAL_AND_RIGHT; if (i == dependencyNum - 1) { branchChar = LIGHT_UP_AND_RIGHT; } var name = dependencies[i].Item.Match.Library.ToString(); var dependencyListStr = string.Join(", ", dependencies[i].Dependencies .Where(isValidDependency) .Select(d => d.Item.Match.Library.ToString())); var format = string.IsNullOrEmpty(dependencyListStr) ? "{0}{1} {2}{3}" : "{0}{1} {2} ({3})"; Reports.Verbose.WriteLine(string.Format(format, branchChar, LIGHT_HORIZONTAL, name, dependencyListStr)); } Reports.Verbose.WriteLine(); }