diff --git a/src/dotnet/commands/dotnet-build/CompilerIOManager.cs b/src/dotnet/commands/dotnet-build/CompilerIOManager.cs index 387f84500..5dfcc52da 100644 --- a/src/dotnet/commands/dotnet-build/CompilerIOManager.cs +++ b/src/dotnet/commands/dotnet-build/CompilerIOManager.cs @@ -74,6 +74,14 @@ namespace Microsoft.DotNet.Tools.Build allOutputPath.Add(path); } } + foreach (var dependency in graphNode.Dependencies) + { + var outputFiles = dependency.ProjectContext + .GetOutputPaths(_configuration, _buildBasePath, _outputPath) + .CompilationFiles; + + inputs.Add(outputFiles.Assembly); + } // output: compiler outputs foreach (var path in allOutputPath) diff --git a/src/dotnet/commands/dotnet-build/DotnetProjectBuilder.cs b/src/dotnet/commands/dotnet-build/DotnetProjectBuilder.cs index 2bc9e507d..c56af82f1 100644 --- a/src/dotnet/commands/dotnet-build/DotnetProjectBuilder.cs +++ b/src/dotnet/commands/dotnet-build/DotnetProjectBuilder.cs @@ -23,7 +23,7 @@ namespace Microsoft.DotNet.Tools.Build private readonly DotNetCommandFactory _commandFactory; private readonly IncrementalManager _incrementalManager; - public DotNetProjectBuilder(BuildCommandApp args) + public DotNetProjectBuilder(BuildCommandApp args): base(args.ShouldSkipDependencies) { _args = args; diff --git a/src/dotnet/commands/dotnet-build/ProjectBuilder.cs b/src/dotnet/commands/dotnet-build/ProjectBuilder.cs index 56bdbd2c9..b06164c5c 100644 --- a/src/dotnet/commands/dotnet-build/ProjectBuilder.cs +++ b/src/dotnet/commands/dotnet-build/ProjectBuilder.cs @@ -12,6 +12,13 @@ namespace Microsoft.DotNet.Tools.Build { internal abstract class ProjectBuilder { + private readonly bool _skipDependencies; + + public ProjectBuilder(bool skipDependencies) + { + _skipDependencies = skipDependencies; + } + private Dictionary _compilationResults = new Dictionary(); public IEnumerable Build(IEnumerable roots) @@ -40,6 +47,7 @@ namespace Microsoft.DotNet.Tools.Build protected virtual void ProjectSkiped(ProjectGraphNode projectNode) { } + protected abstract CompilationResult RunCompile(ProjectGraphNode projectNode); private CompilationResult Build(ProjectGraphNode projectNode) @@ -58,12 +66,15 @@ namespace Microsoft.DotNet.Tools.Build private CompilationResult CompileWithDependencies(ProjectGraphNode projectNode) { - foreach (var dependency in projectNode.Dependencies) + if (!_skipDependencies) { - var result = Build(dependency); - if (result == CompilationResult.Failure) + foreach (var dependency in projectNode.Dependencies) { - return CompilationResult.Failure; + var result = Build(dependency); + if (result == CompilationResult.Failure) + { + return CompilationResult.Failure; + } } } diff --git a/src/dotnet/commands/dotnet-build/ProjectGraphCollector.cs b/src/dotnet/commands/dotnet-build/ProjectGraphCollector.cs index d53ea5d76..c0cd7be12 100644 --- a/src/dotnet/commands/dotnet-build/ProjectGraphCollector.cs +++ b/src/dotnet/commands/dotnet-build/ProjectGraphCollector.cs @@ -36,8 +36,9 @@ namespace Microsoft.DotNet.Tools.Build private ProjectGraphNode TraverseProject(ProjectDescription project, IDictionary lookup, ProjectContext context = null) { + var isRoot = context != null; var deps = new List(); - if (_collectDependencies) + if (isRoot || _collectDependencies) { foreach (var dependency in project.Dependencies) { @@ -55,8 +56,9 @@ namespace Microsoft.DotNet.Tools.Build } } } + var task = context != null ? Task.FromResult(context) : Task.Run(() => _projectContextFactory(project.Path, project.Framework)); - return new ProjectGraphNode(task, deps, context != null); + return new ProjectGraphNode(task, deps, isRoot); } private IEnumerable TraverseNonProject(LibraryDescription root, IDictionary lookup) diff --git a/test/dotnet-build.Tests/BuildProjectToProjectTests.cs b/test/dotnet-build.Tests/BuildProjectToProjectTests.cs index 26d2e72c0..97ec5f9c7 100644 --- a/test/dotnet-build.Tests/BuildProjectToProjectTests.cs +++ b/test/dotnet-build.Tests/BuildProjectToProjectTests.cs @@ -68,7 +68,7 @@ namespace Microsoft.DotNet.Tools.Builder.Tests .WithBuildArtifacts(); TestProjectRoot = testInstance.TestRoot; - + var dependencies = new[] { "L11", "L12", "L21", "L22" }; // modify the source code of a leaf dependency @@ -86,6 +86,27 @@ namespace Microsoft.DotNet.Tools.Builder.Tests AssertResultDoesNotContainStrings(result3, dependencies); } + [Fact] + public void TestNoDependenciesDependencyRebuild() + { + var testInstance = TestAssetsManager.CreateTestInstance("TestProjectToProjectDependencies") + .WithLockFiles() + .WithBuildArtifacts(); + + TestProjectRoot = testInstance.TestRoot; + + // modify the source code of a leaf dependency + TouchSourcesOfProject("L11"); + + // second build with no dependencies, rebuilding leaf + var result2 = new BuildCommand(GetProjectDirectory("L11"), noDependencies: true, framework: DefaultLibraryFramework).ExecuteWithCapturedOutput(); + result2.Should().HaveStdOutMatching("Compiling.*L11.*"); + + // third build with no dependencies but incremental; root project should rebuild + var result3 = BuildProject(noDependencies: true); + result3.Should().HaveCompiledProject("L0", _appFrameworkFullName); + } + private static void AssertResultDoesNotContainStrings(CommandResult commandResult, string[] strings) { foreach (var s in strings)