117 lines
3.7 KiB
C#
117 lines
3.7 KiB
C#
using GlobExpressions;
|
|
using Microsoft.Build.Construction;
|
|
using static SimpleExec.Command;
|
|
|
|
namespace Build;
|
|
|
|
public static class Affected
|
|
{
|
|
public static readonly string Root = Environment.CurrentDirectory;
|
|
public const string AFFECTED_PROJECT = "affected.proj";
|
|
|
|
private static IEnumerable<string> GetAffectedProjects()
|
|
{
|
|
var projFile = Path.Combine(Root, AFFECTED_PROJECT);
|
|
Console.WriteLine("Affected project file: " + projFile);
|
|
var project = ProjectRootElement.Open(projFile) ?? throw new InvalidOperationException();
|
|
var references = project.ItemGroups.SelectMany(x => x.Items).Where(x => x.ItemType == "ProjectReference");
|
|
|
|
foreach (var refe in references)
|
|
{
|
|
var referencePath = refe.Include[(Root.Length + 1)..];
|
|
referencePath = Path.GetDirectoryName(referencePath) ?? throw new InvalidOperationException();
|
|
if (Path.DirectorySeparatorChar != '/')
|
|
{
|
|
referencePath = referencePath.Replace(Path.DirectorySeparatorChar, '/');
|
|
}
|
|
|
|
yield return referencePath;
|
|
}
|
|
}
|
|
|
|
public static async Task<IEnumerable<string>> GetTestProjects()
|
|
{
|
|
await ComputeAffected();
|
|
var projFile = Path.Combine(Root, AFFECTED_PROJECT);
|
|
if (File.Exists(projFile))
|
|
{
|
|
var references = GetAffectedProjects();
|
|
return references.Where(x => x.Contains("Tests"));
|
|
}
|
|
return Glob.Files(Root, "**/*.Tests.csproj");
|
|
}
|
|
|
|
public static async Task<ProjectGroup[]> GetAffectedProjectGroups()
|
|
{
|
|
await ComputeAffected();
|
|
var projFile = Path.Combine(Root, AFFECTED_PROJECT);
|
|
if (File.Exists(projFile))
|
|
{
|
|
var references = GetAffectedProjects().ToList();
|
|
var groups = new List<ProjectGroup>();
|
|
foreach (var projectGroup in Consts.ProjectGroups)
|
|
{
|
|
foreach (var referencePath in references)
|
|
{
|
|
if (projectGroup.Projects.Any(x => x.ProjectPath.Contains(referencePath)))
|
|
{
|
|
groups.Add(projectGroup);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
foreach (var group in groups)
|
|
{
|
|
Console.WriteLine("Affected project group being built: " + group.HostAppSlug);
|
|
}
|
|
|
|
return groups.ToArray();
|
|
}
|
|
|
|
Console.WriteLine("Using all project groups: " + string.Join(',', Consts.ProjectGroups));
|
|
return Consts.ProjectGroups;
|
|
}
|
|
|
|
private static bool s_affectedComputed;
|
|
|
|
public static async Task ComputeAffected()
|
|
{
|
|
if (s_affectedComputed)
|
|
{
|
|
return;
|
|
}
|
|
|
|
var currentTag = await Versions.GetCurrentTag();
|
|
var currentVersion = await Versions.ComputeVersion();
|
|
var lastTag = await Versions.GetPreviousTag(currentTag);
|
|
var lastVersion = await Versions.ComputePreviousVersion(currentTag);
|
|
|
|
Console.WriteLine($"Last tag: {lastTag}, Current tag: {currentTag}");
|
|
Console.WriteLine($"Last parsed version: {lastVersion}, Current parsed version: {currentVersion}");
|
|
|
|
var sort = currentVersion.CompareSortOrderTo(lastVersion);
|
|
if (sort == -1)
|
|
{
|
|
Console.WriteLine($"Current version {currentVersion} is less than: {lastVersion}");
|
|
s_affectedComputed = true;
|
|
return;
|
|
}
|
|
|
|
var majorEquals = currentVersion.Major == lastVersion.Major;
|
|
if (!majorEquals)
|
|
{
|
|
Console.WriteLine($"Current version {currentVersion} is not matching major version: {lastVersion}");
|
|
s_affectedComputed = true;
|
|
return;
|
|
}
|
|
|
|
//use tags no matter the version if major versions match
|
|
var (currentCommit, _) = await ReadAsync("git", $"rev-list -n 1 {currentTag}");
|
|
var (lastCommit, _) = await ReadAsync("git", $"rev-list -n 1 {lastTag}");
|
|
await RunAsync("dotnet", $"affected -v --from {currentCommit.Trim()} --to {lastCommit.Trim()}", Root);
|
|
|
|
s_affectedComputed = true;
|
|
}
|
|
}
|