diff --git a/DotNetSolutionTools.Core/DotNetUpgrade.cs b/DotNetSolutionTools.Core/DotNetUpgrade.cs index d112874..6ba2802 100644 --- a/DotNetSolutionTools.Core/DotNetUpgrade.cs +++ b/DotNetSolutionTools.Core/DotNetUpgrade.cs @@ -2,6 +2,7 @@ using Microsoft.Build.Construction; using Microsoft.Build.Definition; using Microsoft.Build.Evaluation; +using NuGet.Versioning; namespace DotNetSolutionTools.Core; @@ -24,54 +25,71 @@ public static class DotNetUpgrade .PropertyGroups .SelectMany(x => x.Properties) .FirstOrDefault(x => x.Name == "TargetFramework"); - if (targetFramework?.Value is "net7.0" or "net6.0" or "net5.0") + if (targetFramework?.Value is "net8.0" or "net7.0" or "net6.0" or "net5.0") { - targetFramework.Value = "net8.0"; - project.Save(); - FormatCsproj.FormatCsprojFile(project.FullPath); + if (targetFramework.Value is not "net8.0") + { + targetFramework.Value = "net8.0"; + project.Save(); + FormatCsproj.FormatCsprojFile(project.FullPath); + } + await UpdatePackagesToLatest(project); } - - await UpdatePackagesToLatest(project); } } public static async Task UpdatePackagesToLatest(ProjectRootElement project) { - var evalProject = Project.FromProjectRootElement( - project, - new ProjectOptions() { LoadSettings = ProjectLoadSettings.IgnoreMissingImports } - ); - var packages = evalProject.Items.Where(x => x.ItemType == "PackageReference"); - var packageNameAndVersion = packages - .Where(s => s.EvaluatedInclude.StartsWith("Microsoft.")) - .Select( - x => - new - { - Package = x, - Name = x.EvaluatedInclude, - Version = Version.Parse( - x.Metadata.First(s => s.Name == "Version").UnevaluatedValue - ) - } - ) - .ToList(); - - var shouldFormat = false; - foreach (var package in packageNameAndVersion) + Project? evalProject = null; + try { - var latestNugetVersion = await NugetLookup.FetchPackageMetadataAsync(package.Name); - // it will compare 6.8.0.0 to 6.8.0, and says left is newer, we dont want to say its newer, so use the normalized string to make a new version - var normalizedVersion = Version.Parse(latestNugetVersion.ToString()); - if (normalizedVersion > package.Version) + evalProject = Project.FromProjectRootElement( + project, + new ProjectOptions() { LoadSettings = ProjectLoadSettings.IgnoreMissingImports } + ); + var packages = evalProject.Items.Where(x => + x.ItemType == "PackageReference" && x.HasMetadata("Version") && + x.EvaluatedInclude.StartsWith("Microsoft.")).ToList(); + + var packageNameAndVersion = packages + .Select( + x => + new + { + Package = x, + Name = x.EvaluatedInclude, + NugetVersion = NuGetVersion.Parse( + x.Metadata.First(s => s.Name == "Version").UnevaluatedValue + ) + } + ) + .ToList(); + + var shouldSave = false; + foreach (var package in packageNameAndVersion) { - shouldFormat = true; - package.Package.SetMetadataValue("Version", latestNugetVersion.ToString()); + var latestNugetVersion = await NugetLookup.FetchPackageMetadataAsync(package.Name); + + if (latestNugetVersion > package.NugetVersion) + { + shouldSave = true; + package.Package.SetMetadataValue("Version", latestNugetVersion.ToString()); + } + } + + if (shouldSave) + { + project.Save(); + FormatCsproj.FormatCsprojFile(project.FullPath); + } + } + finally + { + if (evalProject is not null) + { + ProjectCollection.GlobalProjectCollection.UnloadProject(evalProject); + ProjectCollection.GlobalProjectCollection.TryUnloadProject(project); } } - - project.Save(); - if (shouldFormat) - FormatCsproj.FormatCsprojFile(project.FullPath); } }