static void Main(string[] args)
        {
            if (!args.Any())
            {
                Console.WriteLine("You did not provide the required targetProject argument.");
                Environment.Exit(1);
            }

            // See if the anonymize flag has been sent
            bool anonymizeNames = args.Any(current => Regex.IsMatch(current.ToLowerInvariant(), @"^[-\/]+([a]{1}|anonymize)$"));

            // See if the Sort Flag has been set
            bool sortOutput = args.Any(current => Regex.IsMatch(current.ToLowerInvariant(), @"^[-\/]+([s]{1}|sort)$"));

            // See if the target project flag has been set
            string targetProject = _ParseForTargetProjectFlag(args);

            string targetArgument = args.First();

            List <string> projectsToEvaluate = new List <string>();

            if (Path.GetExtension(targetArgument).Equals(".sln", StringComparison.InvariantCultureIgnoreCase))
            {
                IEnumerable <string> projectsInSolution = MSBuildUtilities.GetProjectsFromSolution(targetArgument);

                // These come back as relative paths; we need to "expand" them
                // otherwise we'll get duplicates when we go to resolve.
                projectsInSolution = PathUtilities.ResolveRelativePaths(projectsInSolution);

                projectsToEvaluate.AddRange(projectsInSolution);
            }
            else
            {
                // Assume its just a single project
                projectsToEvaluate.Add(targetArgument);
            }

            Dictionary <string, IEnumerable <string> > projectReferenceDependencies = MSBPRDependencyGraph.ResolveProjectReferenceDependencies(projectsToEvaluate);

            string output = MSBPRDependencyGraph.CreateDOTGraph(projectReferenceDependencies, targetProject, anonymizeNames, sortOutput, false);

            Console.WriteLine(output);
        }
        /// <summary>
        /// Given a IEnumerable of Target Project Files, return all Package References.
        /// </summary>
        /// <param name="targetProjects">An IEnumerable of strings that represent MSBuild Projects.</param>
        /// <returns>A Dictionary in which the Key is the Project Path, and the Value is an IEnumerable of all its referenced Packages</returns>
        internal static Dictionary <string, IEnumerable <string> > ResolvePackageReferenceDependencies(IEnumerable <string> targetProjects)
        {
            ConcurrentBag <KeyValuePair <string, IEnumerable <string> > > resolvedPackageReferences = new ConcurrentBag <KeyValuePair <string, IEnumerable <string> > >();

            // Because of the large number of projects that could be scanned perform this in parallel.
            Parallel.ForEach(targetProjects, targetProject =>
            {
                IEnumerable <string> currentProjectPackageReferences       = MSBuildUtilities.PackageReferences(targetProject);
                KeyValuePair <string, IEnumerable <string> > currentResult = new KeyValuePair <string, IEnumerable <string> >(targetProject, currentProjectPackageReferences);
                resolvedPackageReferences.Add(currentResult);
            }
                             );

            // Convert this into the Dictionary
            Dictionary <string, IEnumerable <string> > result = new Dictionary <string, IEnumerable <string> >();

            foreach (KeyValuePair <string, IEnumerable <string> > kvp in resolvedPackageReferences)
            {
                result.Add(kvp.Key, kvp.Value);
            }

            return(result);
        }
        /// <summary>
        /// Given a IEnumerable of Target Project Files, Resolve All N-Order ProjectReference Dependencies.
        /// </summary>
        /// <param name="targetProjects">An IEnumerable of strings that represent MSBuild Projects.</param>
        /// <returns>A Dictionary in which the Key is the Project, and the Value is an IEnumerable of all its Project Reference projects</returns>
        internal static Dictionary <string, IEnumerable <string> > ResolveProjectReferenceDependencies(IEnumerable <string> targetProjects)
        {
            Stack <string> unresolvedProjects = new Stack <string>();
            Dictionary <string, IEnumerable <string> > resolvedProjects = new Dictionary <string, IEnumerable <string> >();

            // Load up the initial projects to the stack
            foreach (string targetProject in targetProjects.Distinct())
            {
                unresolvedProjects.Push(targetProject);
            }

            while (unresolvedProjects.Count > 0)
            {
                string currentProject = unresolvedProjects.Pop();

                // First check just to make sure it wasn't already resolved.
                if (!resolvedProjects.ContainsKey(currentProject))
                {
                    // Get all this projects references
                    string[] projectDependencies = MSBuildUtilities.ProjectDependencies(currentProject).ToArray();

                    resolvedProjects.Add(currentProject, projectDependencies);

                    foreach (string projectDependency in projectDependencies)
                    {
                        // Save the stack by not resolving already resolved projects
                        if (!resolvedProjects.ContainsKey(projectDependency))
                        {
                            unresolvedProjects.Push(projectDependency);
                        }
                    }
                }
            }

            return(resolvedProjects);
        }
示例#4
0
        static void Main(string[] args)
        {
            string targetFile = string.Empty;
            bool   showHelp   = false;

            // Create an Options Object
            MSBPROptions options = new MSBPROptions();

            OptionSet p = new OptionSet()
            {
                { "<>", Strings.TargetArgumentDescription, v => targetFile = v },
                { "a|anonymize", Strings.AnonymizeDescription, v => options.AnonymizeNames = v != null },
                { "sA|ShowAllReferences", Strings.ShowAllReferencesDescription, v => { if (v != null)
                                                                                       {
                                                                                           options.ShowAssemblyReferences = true; options.ShowPackageReferences = true;
                                                                                       }
                  } },
                { "sar|ShowAssemblyReferences", Strings.ShowAssemblyReferencesDescription, v => options.ShowAssemblyReferences = v != null },
                { "spr|ShowPackageReferences", Strings.ShowPackageReferencesDescription, v => options.ShowPackageReferences = v != null },
                { "s|sort", Strings.SortDescription, v => options.SortProjects = v != null },
                { "?|h|help", Strings.HelpDescription, v => showHelp = v != null },
            };

            try
            {
                p.Parse(args);
            }
            catch (OptionException)
            {
                Console.WriteLine(Strings.ShortUsageMessage);
                Console.WriteLine($"Try `{Strings.ProgramName} --help` for more information.");
                return;
            }

            if (showHelp || string.IsNullOrEmpty(targetFile))
            {
                Environment.ExitCode = ShowUsage(p);
            }
            else if (!File.Exists(targetFile))
            {
                Console.WriteLine(Strings.InvalidTargetArgument, targetFile);
                Environment.ExitCode = 9009;
            }
            else
            {
                List <string> projectsToEvaluate = new List <string>();

                if (Path.GetExtension(targetFile).Equals(".sln", StringComparison.InvariantCultureIgnoreCase))
                {
                    IEnumerable <string> projectsInSolution = MSBuildUtilities.GetProjectsFromSolution(targetFile);

                    // These come back as relative paths; we need to "expand" them
                    // otherwise we'll get duplicates when we go to resolve.
                    projectsInSolution = projectsInSolution.Select(relativeProjectPath => Path.GetFullPath(relativeProjectPath));

                    projectsToEvaluate.AddRange(projectsInSolution);
                }
                else
                {
                    // Assume its just a single project
                    FileInfo fi = new FileInfo(targetFile);
                    projectsToEvaluate.Add(fi.FullName);
                }

                Dictionary <string, IEnumerable <string> > projectReferenceDependencies = MSBPRDependencyGraph.ResolveProjectReferenceDependencies(projectsToEvaluate);

                string output = MSBPRDependencyGraph.CreateDOTGraph(projectReferenceDependencies, options);

                Console.WriteLine(output);
            }
        }