Exemple #1
0
        public static int Compare(AssemblyReflectionInput assembly1Input, AssemblyReflectionInput assembly2Input, string outputApiPath = null, SemverChangeType?expectedChangeType = null, bool useDependencyChanges = false)
        {
            return(CompareAction(assembly1Input, assembly2Input, (assembly1, assembly2) =>
            {
                var assembly1Semver = GetSemanticVersion(assembly1);
                var assembly2Semver = GetSemanticVersion(assembly2);

                var compareResult = ComparePublicApi(assembly1, assembly2);

                var dependencyCompareResult = CompareDependencies(assembly1, assembly2);

                if (useDependencyChanges && dependencyCompareResult > compareResult)
                {
                    compareResult = dependencyCompareResult;
                }

                if (!string.IsNullOrWhiteSpace(outputApiPath) && Directory.Exists(outputApiPath))
                {
                    var path1 = GetSafeApiFileName(outputApiPath, assembly1.GetName().Name, assembly1Semver, ".api.txt");
                    var path2 = GetSafeApiFileName(outputApiPath, assembly2.GetName().Name, assembly2Semver, ".api.txt");
                    if (path2.Equals(path1, StringComparison.OrdinalIgnoreCase))
                    {
                        path1 = Path.Join(Path.GetDirectoryName(path1), Path.GetFileNameWithoutExtension(path1), "(1)", Path.GetExtension(path1));
                        path2 = Path.Join(Path.GetDirectoryName(path2), Path.GetFileNameWithoutExtension(path2), "(2)", Path.GetExtension(path2));
                    }
                    WriteApiToFile(assembly1, path1);
                    WriteApiToFile(assembly2, path2);
                }

                var calculatedSemver = CalculateSemver(assembly1Semver, compareResult);

                if (expectedChangeType.HasValue)
                {
                    if (expectedChangeType >= compareResult || assembly1Semver.IsPrerelease)
                    {
                        Console.ForegroundColor = ConsoleColor.Green;
                        Console.WriteLine();
                        Console.WriteLine($"Valid [{expectedChangeType}] semver change for {assembly1.GetName().Name} {assembly1Semver.ToShortVerion()} => {assembly2.GetName().Name} {assembly2Semver.ToShortVerion()}. Calculated as [{compareResult}] ({calculatedSemver})");
                        Console.ResetColor();
                        return 0;
                    }
                    else
                    {
                        Console.ForegroundColor = ConsoleColor.Red;
                        Console.WriteLine();
                        Console.WriteLine($"Changes for {assembly1.GetName().Name} {assembly1Semver.ToShortVerion()} => {assembly2.GetName().Name} {assembly2Semver.ToShortVerion()} do not meet semver guidelines for a [{expectedChangeType}] change.  Calculated as [{compareResult}] ({calculatedSemver})");
                        Console.ResetColor();
                        return 1;
                    }
                }
                else
                {
                    Console.WriteLine();
                    Console.WriteLine($"The calculated semver for {assembly1.GetName().Name} {assembly1Semver.ToShortVerion()} => {assembly2.GetName().Name} {assembly2Semver.ToShortVerion()} is [{compareResult}] ({calculatedSemver})");
                    return 0;
                }
            }));
        }
Exemple #2
0
        private static int CompareAction(AssemblyReflectionInput assembly1Input, AssemblyReflectionInput assembly2Input, Func <Assembly, Assembly, int> compareFunc)
        {
            var assembly1Paths = new[] { assembly1Input.AssemblyPath }.Concat(assembly1Input.AssemblyDependencies).Distinct();
            var assembly2Paths = new[] { assembly2Input.AssemblyPath }.Concat(assembly2Input.AssemblyDependencies).Distinct();

            using var loadContext1 = new MetadataLoadContext(new PathAssemblyResolver(assembly1Paths));
            using var loadContext2 = new MetadataLoadContext(new PathAssemblyResolver(assembly2Paths));

            var assembly1 = loadContext1.LoadFromAssemblyPath(assembly1Input.AssemblyPath);
            var assembly2 = loadContext2.LoadFromAssemblyPath(assembly2Input.AssemblyPath);

            return(compareFunc(assembly1, assembly2));
        }
Exemple #3
0
        public static int WritePublicApi(AssemblyReflectionInput input, string outputApiPath)
        {
            var assembly1Paths = new[] { input.AssemblyPath }.Concat(input.AssemblyDependencies).Distinct();

            using (var loadContext1 = new MetadataLoadContext(new PathAssemblyResolver(assembly1Paths)))
            {
                var assembly1       = loadContext1.LoadFromAssemblyPath(input.AssemblyPath);
                var assembly1Semver = GetSemanticVersion(assembly1);

                WriteApiToFile(assembly1, GetSafeApiFileName(outputApiPath, input.AssemblyPath, assembly1Semver, ".api.txt"));
                WriteSignaturesToFile(assembly1, GetSafeApiFileName(outputApiPath, input.AssemblyPath, assembly1Semver, ".signatures.txt"));
            }

            return(0);
        }