public IEnumerable<ContributorCall> GenerateCallGraph(IEnumerable<IPipelineContributor> contributors) { contributors = contributors.ToList(); var bootstrapper = contributors.OfType<KnownStages.IBegin>().Single(); var nodes = new List<TopologicalNode<ContributorNotification>>(); foreach (var contributor in contributors.Where(x => x != bootstrapper)) { var builder = new PipelineBuilder(contributors); builder.ContributorRegistrations.Clear(); contributor.Initialize(builder); nodes.AddRange( builder.ContributorRegistrations .DefaultIfEmpty(new Notification( Middleware.IdentitySingleTap, builder.Contributors)) .Select(reg => new TopologicalNode<ContributorNotification>( new ContributorNotification(contributor, reg)))); } foreach (var notificationNode in nodes) { foreach (var afterType in notificationNode.Item.Notification.AfterTypes) { var parents = GetCompatibleNodes(nodes, notificationNode, afterType); notificationNode.Dependencies.AddRange(parents); } foreach (var beforeType in notificationNode.Item.Notification.BeforeTypes) { var children = GetCompatibleNodes(nodes, notificationNode, beforeType); foreach (var child in children) { child.Dependencies.Add(notificationNode); } } } var rootItem = new ContributorNotification(bootstrapper, new Notification(Middleware.IdentitySingleTap, contributors)); return new TopologicalTree<ContributorNotification>(rootItem, nodes).Nodes .Select( n => new ContributorCall(n.Item.Contributor, n.Item.Notification.Target, n.Item.Notification.Description)); }
public IEnumerable<ContributorCall> GenerateCallGraph(IEnumerable<IPipelineContributor> contributors) { contributors = contributors.ToList(); var bootstrapper = contributors.OfType<KnownStages.IBegin>().Single(); var tree = new DependencyTree<ContributorNotification>( new ContributorNotification(bootstrapper, new Notification(Middleware.IdentitySingleTap, contributors))); foreach (var contrib in contributors.Where(x => x != bootstrapper)) { var builder = new PipelineBuilder(contributors); builder.ContributorRegistrations.Clear(); contrib.Initialize(builder); var contributorRegistrations = builder.ContributorRegistrations.DefaultIfEmpty(new Notification(Middleware.IdentitySingleTap, contributors)).ToList(); foreach (var registration in contributorRegistrations) { tree.CreateNode(new ContributorNotification(contrib, registration)); } } foreach (var notificationNode in tree.Nodes) { foreach (var parentNode in GetCompatibleTypes(tree, notificationNode, notificationNode.Value.Notification.AfterTypes)) parentNode.ChildNodes.Add(notificationNode); foreach (var childNode in GetCompatibleTypes(tree, notificationNode, notificationNode.Value.Notification.BeforeTypes)) childNode.ParentNodes.Add(notificationNode); } return tree.GetCallGraph() .Select( x => new ContributorCall(x.Value.Contributor, x.Value.Notification.Target, x.Value.Notification.Description)); }