зеркало из https://github.com/dotnet/sdk.git
881 строка
36 KiB
C#
881 строка
36 KiB
C#
// Licensed to the .NET Foundation under one or more agreements.
|
|
// The .NET Foundation licenses this file to you under the MIT license.
|
|
|
|
|
|
using NuGet.Common;
|
|
using NuGet.Frameworks;
|
|
using NuGet.ProjectModel;
|
|
|
|
namespace Microsoft.NET.Build.Tests
|
|
{
|
|
public class GivenThereAreDefaultItems : SdkTest
|
|
{
|
|
public GivenThereAreDefaultItems(ITestOutputHelper log) : base(log)
|
|
{
|
|
}
|
|
|
|
[Fact]
|
|
public void It_ignores_excluded_folders()
|
|
{
|
|
Action<GetValuesCommand> setup = getValuesCommand =>
|
|
{
|
|
foreach (string folder in new[] { "bin", "obj", ".vscode" })
|
|
{
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, folder, "source.cs"),
|
|
"!InvalidCSharp!");
|
|
}
|
|
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "Code", "Class1.cs"),
|
|
"public class Class1 {}");
|
|
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "Packages", "Package.cs"),
|
|
"public class Package {}");
|
|
};
|
|
|
|
var compileItems = GivenThatWeWantToBuildALibrary.GetValuesFromTestLibrary(Log, _testAssetsManager, "Compile", setup);
|
|
|
|
RemoveGeneratedCompileItems(compileItems);
|
|
|
|
var expectedItems = new[]
|
|
{
|
|
"Helper.cs",
|
|
@"Code\Class1.cs",
|
|
@"Packages\Package.cs"
|
|
}
|
|
.Select(item => item.Replace('\\', Path.DirectorySeparatorChar))
|
|
.ToArray();
|
|
|
|
compileItems.Should().BeEquivalentTo(expectedItems);
|
|
}
|
|
|
|
[Fact]
|
|
public void It_excludes_items_in_a_custom_outputpath()
|
|
{
|
|
Action<GetValuesCommand> setup = getValuesCommand =>
|
|
{
|
|
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "Output", "CSharpInOutput.cs"),
|
|
"!InvalidCSharp!");
|
|
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "Code", "Class1.cs"),
|
|
"public class Class1 {}");
|
|
};
|
|
|
|
Action<XDocument> projectChanges = project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
var propertyGroup = new XElement(ns + "PropertyGroup");
|
|
project.Root.Add(propertyGroup);
|
|
propertyGroup.Add(new XElement(ns + "OutputPath", "Output"));
|
|
};
|
|
|
|
|
|
var compileItems = GivenThatWeWantToBuildALibrary.GetValuesFromTestLibrary(Log, _testAssetsManager, "Compile", setup, projectChanges: projectChanges);
|
|
|
|
RemoveGeneratedCompileItems(compileItems);
|
|
|
|
var expectedItems = new[]
|
|
{
|
|
"Helper.cs",
|
|
@"Code\Class1.cs"
|
|
}
|
|
.Select(item => item.Replace('\\', Path.DirectorySeparatorChar))
|
|
.ToArray();
|
|
|
|
compileItems.Should().BeEquivalentTo(expectedItems);
|
|
}
|
|
|
|
[Fact]
|
|
public void It_allows_excluded_folders_to_be_overridden()
|
|
{
|
|
Action<GetValuesCommand> setup = getValuesCommand =>
|
|
{
|
|
foreach (string folder in new[] { "bin", "obj", "packages" })
|
|
{
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, folder, "source.cs"),
|
|
$"public class ClassFrom_{folder} {{}}");
|
|
}
|
|
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "Code", "Class1.cs"),
|
|
"public class Class1 {}");
|
|
};
|
|
|
|
Action<XDocument> projectChanges = project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
project.Root.Element(ns + "PropertyGroup").Add(new XElement(ns + "EnableDefaultItems", "False"));
|
|
|
|
XElement itemGroup = new(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
itemGroup.Add(new XElement(ns + "Compile", new XAttribute("Include", "**\\*.cs")));
|
|
};
|
|
|
|
var compileItems = GivenThatWeWantToBuildALibrary.GetValuesFromTestLibrary(Log, _testAssetsManager,
|
|
"Compile", setup, new[] { "/p:DisableDefaultRemoves=true" }, GetValuesCommand.ValueType.Item,
|
|
projectChanges: projectChanges);
|
|
|
|
RemoveGeneratedCompileItems(compileItems);
|
|
|
|
var expectedItems = new[]
|
|
{
|
|
"Helper.cs",
|
|
@"Code\Class1.cs",
|
|
@"bin\source.cs",
|
|
@"obj\source.cs",
|
|
@"packages\source.cs"
|
|
}
|
|
.Select(item => item.Replace('\\', Path.DirectorySeparatorChar))
|
|
.ToArray();
|
|
|
|
compileItems.Should().BeEquivalentTo(expectedItems);
|
|
}
|
|
|
|
[Fact]
|
|
public void It_allows_items_outside_project_root_to_be_included()
|
|
{
|
|
Action<GetValuesCommand> setup = getValuesCommand =>
|
|
{
|
|
string sharedCodePath = Path.Combine(Path.GetDirectoryName(getValuesCommand.ProjectRootPath), "Shared");
|
|
WriteFile(Path.Combine(sharedCodePath, "Shared.cs"),
|
|
"public class SharedClass {}");
|
|
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "Code", "Class1.cs"),
|
|
"public class Class1 {}");
|
|
};
|
|
|
|
Action<XDocument> projectChanges = project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
XElement itemGroup = new(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
itemGroup.Add(new XElement(ns + "Compile", new XAttribute("Include", "..\\Shared\\**\\*.cs")));
|
|
};
|
|
|
|
var compileItems = GivenThatWeWantToBuildALibrary.GetValuesFromTestLibrary(Log, _testAssetsManager, "Compile", setup, projectChanges: projectChanges);
|
|
|
|
RemoveGeneratedCompileItems(compileItems);
|
|
|
|
var expectedItems = new[]
|
|
{
|
|
"Helper.cs",
|
|
@"Code\Class1.cs",
|
|
@"..\Shared\Shared.cs",
|
|
}
|
|
.Select(item => item.Replace('\\', Path.DirectorySeparatorChar))
|
|
.ToArray();
|
|
|
|
compileItems.Should().BeEquivalentTo(expectedItems);
|
|
}
|
|
|
|
[Fact]
|
|
public void It_allows_a_project_subfolder_to_be_excluded()
|
|
{
|
|
Action<GetValuesCommand> setup = getValuesCommand =>
|
|
{
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "Code", "Class1.cs"),
|
|
"public class Class1 {}");
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "Excluded", "Excluded.cs"),
|
|
"!InvalidCSharp!");
|
|
};
|
|
|
|
Action<XDocument> projectChanges = project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
XElement itemGroup = new(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
itemGroup.Add(new XElement(ns + "Compile", new XAttribute("Remove", "Excluded\\**\\*.cs")));
|
|
};
|
|
|
|
var compileItems = GivenThatWeWantToBuildALibrary.GetValuesFromTestLibrary(Log, _testAssetsManager, "Compile", setup, projectChanges: projectChanges);
|
|
|
|
RemoveGeneratedCompileItems(compileItems);
|
|
|
|
var expectedItems = new[]
|
|
{
|
|
"Helper.cs",
|
|
@"Code\Class1.cs",
|
|
}
|
|
.Select(item => item.Replace('\\', Path.DirectorySeparatorChar))
|
|
.ToArray();
|
|
|
|
compileItems.Should().BeEquivalentTo(expectedItems);
|
|
}
|
|
|
|
[Fact]
|
|
public void It_allows_files_in_the_obj_folder_to_be_explicitly_included()
|
|
{
|
|
Action<GetValuesCommand> setup = getValuesCommand =>
|
|
{
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "Code", "Class1.cs"),
|
|
"public class Class1 {}");
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "obj", "Class2.cs"),
|
|
"public class Class2 {}");
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "obj", "Excluded.cs"),
|
|
"!InvalidCSharp!");
|
|
};
|
|
|
|
Action<XDocument> projectChanges = project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
XElement itemGroup = new(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
itemGroup.Add(new XElement(ns + "Compile", new XAttribute("Include", "obj\\Class2.cs")));
|
|
};
|
|
|
|
var compileItems = GivenThatWeWantToBuildALibrary.GetValuesFromTestLibrary(Log, _testAssetsManager, "Compile", setup, projectChanges: projectChanges);
|
|
|
|
RemoveGeneratedCompileItems(compileItems);
|
|
|
|
var expectedItems = new[]
|
|
{
|
|
"Helper.cs",
|
|
@"Code\Class1.cs",
|
|
@"obj\Class2.cs"
|
|
}
|
|
.Select(item => item.Replace('\\', Path.DirectorySeparatorChar))
|
|
.ToArray();
|
|
|
|
compileItems.Should().BeEquivalentTo(expectedItems);
|
|
}
|
|
|
|
[Fact]
|
|
public void It_allows_a_CSharp_file_to_be_used_as_an_EmbeddedResource()
|
|
{
|
|
Action<GetValuesCommand> setup = getValuesCommand =>
|
|
{
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "Code", "Class1.cs"),
|
|
"public class Class1 {}");
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "CSharpAsResource.cs"),
|
|
"public class CSharpAsResource {}");
|
|
};
|
|
|
|
Action<XDocument> projectChanges = project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
XElement itemGroup = new(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
itemGroup.Add(new XElement(ns + "EmbeddedResource", new XAttribute("Include", "CSharpAsResource.cs")));
|
|
itemGroup.Add(new XElement(ns + "Compile", new XAttribute("Remove", "CSharpAsResource.cs")));
|
|
};
|
|
|
|
var compileItems = GivenThatWeWantToBuildALibrary.GetValuesFromTestLibrary(Log, _testAssetsManager, "Compile", setup, projectChanges: projectChanges);
|
|
|
|
RemoveGeneratedCompileItems(compileItems);
|
|
|
|
var expectedItems = new[]
|
|
{
|
|
"Helper.cs",
|
|
@"Code\Class1.cs",
|
|
}
|
|
.Select(item => item.Replace('\\', Path.DirectorySeparatorChar))
|
|
.ToArray();
|
|
|
|
compileItems.Should().BeEquivalentTo(expectedItems);
|
|
|
|
|
|
var embeddedResourceItems = GivenThatWeWantToBuildALibrary.GetValuesFromTestLibrary(Log, _testAssetsManager, "EmbeddedResource", setup, projectChanges: projectChanges, identifier: "EmbeddedResource");
|
|
|
|
var expectedEmbeddedResourceItems = new[]
|
|
{
|
|
"CSharpAsResource.cs"
|
|
}
|
|
.Select(item => item.Replace('\\', Path.DirectorySeparatorChar))
|
|
.ToArray();
|
|
|
|
embeddedResourceItems.Should().BeEquivalentTo(expectedEmbeddedResourceItems);
|
|
}
|
|
|
|
[Fact]
|
|
public void It_allows_a_CSharp_file_to_be_used_as_Content()
|
|
{
|
|
Action<GetValuesCommand> setup = getValuesCommand =>
|
|
{
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "Code", "Class1.cs"),
|
|
"public class Class1 {}");
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "CSharpAsContent.cs"),
|
|
"public class CSharpAsContent {}");
|
|
|
|
WriteFile(Path.Combine(getValuesCommand.ProjectRootPath, "None.txt"), "Content file");
|
|
};
|
|
|
|
Action<XDocument> projectChanges = project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
XElement itemGroup = new(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
itemGroup.Add(new XElement(ns + "Content", new XAttribute("Include", "CSharpAsContent.cs"),
|
|
new XAttribute("CopyToOutputDirectory", "true")));
|
|
itemGroup.Add(new XElement(ns + "Compile", new XAttribute("Remove", "CSharpAsContent.cs")));
|
|
};
|
|
|
|
var compileItems = GivenThatWeWantToBuildALibrary.GetValuesFromTestLibrary(Log, _testAssetsManager, "Compile", setup, projectChanges: projectChanges);
|
|
|
|
RemoveGeneratedCompileItems(compileItems);
|
|
|
|
var expectedItems = new[]
|
|
{
|
|
"Helper.cs",
|
|
@"Code\Class1.cs",
|
|
}
|
|
.Select(item => item.Replace('\\', Path.DirectorySeparatorChar))
|
|
.ToArray();
|
|
|
|
compileItems.Should().BeEquivalentTo(expectedItems);
|
|
|
|
|
|
var contentItems = GivenThatWeWantToBuildALibrary.GetValuesFromTestLibrary(Log, _testAssetsManager, "Content", setup, projectChanges: projectChanges, identifier: "Content");
|
|
|
|
var expectedContentItems = new[]
|
|
{
|
|
"CSharpAsContent.cs",
|
|
}
|
|
.Select(item => item.Replace('\\', Path.DirectorySeparatorChar))
|
|
.ToArray();
|
|
|
|
contentItems.Should().BeEquivalentTo(expectedContentItems);
|
|
|
|
var noneItems = GivenThatWeWantToBuildALibrary.GetValuesFromTestLibrary(Log, _testAssetsManager, "None", setup, projectChanges: projectChanges, identifier: expectedContentItems.GetHashCode().ToString());
|
|
|
|
var expectedNoneItems = new[]
|
|
{
|
|
"None.txt"
|
|
}
|
|
.Select(item => item.Replace('\\', Path.DirectorySeparatorChar))
|
|
.ToArray();
|
|
|
|
noneItems.Should().BeEquivalentTo(expectedNoneItems);
|
|
}
|
|
|
|
[Fact]
|
|
public void It_does_not_include_items_in_any_group_if_group_specific_default_include_properties_are_false()
|
|
{
|
|
var testProject = new TestProject()
|
|
{
|
|
Name = "DontIncludeSourceFilesInNone",
|
|
TargetFrameworks = ToolsetInfo.CurrentTargetFramework,
|
|
IsExe = true,
|
|
};
|
|
testProject.AdditionalProperties["EnableDefaultCompileItems"] = "false";
|
|
testProject.AdditionalProperties["EnableDefaultResourceItems"] = "false";
|
|
|
|
// Windows App SDK related
|
|
testProject.AdditionalProperties["EnableDefaultWindowsAppSdkContentItems"] = "true";
|
|
testProject.AdditionalProperties["EnableDefaultWindowsAppSdkPRIResourceItems"] = "true";
|
|
testProject.AdditionalProperties["EnableDefaultContentItems"] = "false";
|
|
testProject.AdditionalProperties["EnableDefaultPRIResourceItems"] = "false";
|
|
|
|
var testAsset = _testAssetsManager.CreateTestProject(testProject)
|
|
.WithProjectChanges(project =>
|
|
{
|
|
// "Manual" include via project file modification.
|
|
var ns = project.Root.Name.Namespace;
|
|
XElement itemGroup = new(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
itemGroup.Add(new XElement(ns + "Compile", new XAttribute("Include", testProject.Name + ".cs")));
|
|
itemGroup.Add(new XElement(ns + "Compile", new XAttribute("Include", testProject.Name + "Program.cs")));
|
|
});
|
|
|
|
var projectFolder = Path.Combine(testAsset.TestRoot, testProject.Name);
|
|
|
|
File.WriteAllText(Path.Combine(projectFolder, "ShouldBeIgnored.cs"), "!InvalidCSharp!");
|
|
File.WriteAllText(Path.Combine(projectFolder, "Resources.resx"), "<Resource/>");
|
|
File.WriteAllText(Path.Combine(projectFolder, "ResourcesResw.resw"), "<root/>");
|
|
File.WriteAllText(Path.Combine(projectFolder, "TestImage.jpg"), "");
|
|
|
|
// Validate Compile items.
|
|
var getCompileItemsCommand = new GetValuesCommand(Log, projectFolder, testProject.TargetFrameworks, "Compile", GetValuesCommand.ValueType.Item);
|
|
getCompileItemsCommand.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
var compileItems = getCompileItemsCommand.GetValues();
|
|
RemoveGeneratedCompileItems(compileItems);
|
|
compileItems.Should().BeEquivalentTo(new[] { testProject.Name + ".cs", testProject.Name + "Program.cs" });
|
|
|
|
// Validate None items.
|
|
var getNoneItemsCommand = new GetValuesCommand(Log, projectFolder, testProject.TargetFrameworks, "None", GetValuesCommand.ValueType.Item);
|
|
getNoneItemsCommand.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
getNoneItemsCommand.GetValues()
|
|
.Should().BeEmpty();
|
|
|
|
// Validate Resource items.
|
|
var getResourceItemsCommand = new GetValuesCommand(Log, projectFolder, testProject.TargetFrameworks, "Resource", GetValuesCommand.ValueType.Item);
|
|
getResourceItemsCommand.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
getResourceItemsCommand.GetValues()
|
|
.Should().BeEmpty();
|
|
|
|
// Validate PRIResource items.
|
|
var getPRIResourceItemsCommand = new GetValuesCommand(Log, projectFolder, testProject.TargetFrameworks, "PRIResource", GetValuesCommand.ValueType.Item);
|
|
getPRIResourceItemsCommand.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
getPRIResourceItemsCommand.GetValues()
|
|
.Should().BeEmpty();
|
|
|
|
// Validate Content items.
|
|
var getContentItemsCommand = new GetValuesCommand(Log, projectFolder, testProject.TargetFrameworks, "Content", GetValuesCommand.ValueType.Item);
|
|
getContentItemsCommand.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
getContentItemsCommand.GetValues()
|
|
.Should().BeEmpty();
|
|
}
|
|
|
|
[Fact]
|
|
public void Default_items_have_the_correct_relative_paths()
|
|
{
|
|
Action<XDocument> projectChanges = project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
var propertyGroup = new XElement(ns + "PropertyGroup");
|
|
project.Root.Add(propertyGroup);
|
|
propertyGroup.Add(new XElement(ns + "EnableDefaultContentItems", "false"));
|
|
|
|
// Copy all None items to output directory
|
|
var itemGroup = new XElement(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
itemGroup.Add(new XElement(ns + "None", new XAttribute("Update", "@(None)"), new XAttribute("CopyToOutputDirectory", "PreserveNewest")));
|
|
};
|
|
|
|
var testAsset = _testAssetsManager
|
|
.CopyTestAsset("AppWithLibrary")
|
|
.WithSource()
|
|
.WithProjectChanges(projectChanges);
|
|
|
|
var buildCommand = new BuildCommand(testAsset, "TestLibrary");
|
|
|
|
WriteFile(Path.Combine(buildCommand.ProjectRootPath, "ProjectRoot.txt"), "ProjectRoot");
|
|
WriteFile(Path.Combine(buildCommand.ProjectRootPath, "Subfolder", "ProjectSubfolder.txt"), "ProjectSubfolder");
|
|
WriteFile(Path.Combine(buildCommand.ProjectRootPath, "wwwroot", "wwwroot.txt"), "wwwroot");
|
|
WriteFile(Path.Combine(buildCommand.ProjectRootPath, "wwwroot", "wwwsubfolder", "wwwsubfolder.txt"), "wwwsubfolder");
|
|
|
|
buildCommand
|
|
.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
var outputDirectory = buildCommand.GetOutputDirectory("netstandard1.5");
|
|
|
|
outputDirectory.Should().OnlyHaveFiles(new[] {
|
|
"TestLibrary.dll",
|
|
"TestLibrary.pdb",
|
|
"TestLibrary.deps.json",
|
|
"ProjectRoot.txt",
|
|
"Subfolder/ProjectSubfolder.txt",
|
|
"wwwroot/wwwroot.txt",
|
|
"wwwroot/wwwsubfolder/wwwsubfolder.txt",
|
|
});
|
|
}
|
|
|
|
[RequiresMSBuildVersionFact("17.1.0.60101")]
|
|
public void Compile_items_can_be_explicitly_specified_while_default_EmbeddedResource_items_are_used()
|
|
{
|
|
Action<XDocument> projectChanges = project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
project.Root.Element(ns + "PropertyGroup").Add(
|
|
new XElement(ns + "EnableDefaultCompileItems", "false"));
|
|
|
|
var itemGroup = new XElement(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
itemGroup.Add(new XElement(ns + "Compile", new XAttribute("Include", "Program.cs")));
|
|
};
|
|
|
|
Action<BuildCommand> setup = buildCommand =>
|
|
{
|
|
WriteFile(Path.Combine(buildCommand.ProjectRootPath, "ShouldNotBeCompiled.cs"),
|
|
"!InvalidCSharp!");
|
|
};
|
|
|
|
GivenThatWeWantAllResourcesInSatellite.TestSatelliteResources(Log, _testAssetsManager, projectChanges, setup, "ExplicitCompileDefaultEmbeddedResource");
|
|
}
|
|
|
|
[Fact]
|
|
public void It_gives_an_error_message_if_duplicate_compile_items_are_included()
|
|
{
|
|
var testProject = new TestProject()
|
|
{
|
|
Name = "DuplicateCompileItems",
|
|
TargetFrameworks = "netstandard1.6",
|
|
};
|
|
|
|
var testAsset = _testAssetsManager.CreateTestProject(testProject)
|
|
.WithProjectChanges(project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
var itemGroup = new XElement(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
itemGroup.Add(new XElement(ns + "Compile", new XAttribute("Include", @"**\*.cs")));
|
|
});
|
|
|
|
var buildCommand = new BuildCommand(testAsset);
|
|
|
|
WriteFile(Path.Combine(buildCommand.ProjectRootPath, "Class1.cs"), "public class Class1 {}");
|
|
|
|
buildCommand
|
|
.Execute()
|
|
.Should()
|
|
.Fail()
|
|
.And.HaveStdOutContaining("DuplicateCompileItems.cs")
|
|
.And.HaveStdOutContaining("Class1.cs")
|
|
.And.HaveStdOutContaining("EnableDefaultCompileItems");
|
|
}
|
|
|
|
[Fact]
|
|
public void Implicit_package_references_are_overridden_by_PackageReference_includes_in_the_project_file()
|
|
{
|
|
var testProject = new TestProject()
|
|
{
|
|
// Underscore is in the project name so we can verify that the warning message output contained "PackageReference"
|
|
Name = "DeduplicatePackage_Reference",
|
|
TargetFrameworks = "netstandard1.6",
|
|
};
|
|
|
|
var testAsset = _testAssetsManager.CreateTestProject(testProject, "DeduplicatePackage_Reference")
|
|
.WithProjectChanges(project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
// Set the implicit package reference version to something that doesn't exist to verify that the Include
|
|
// in the project file overrides the implicit one
|
|
project.Root.Element(ns + "PropertyGroup").Add(
|
|
new XElement(ns + "NetStandardImplicitPackageVersion", "0.1.0-does-not-exist"));
|
|
|
|
var itemGroup = new XElement(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
|
|
// Use non-standard casing for the explicit package reference to verify that comparison is case-insensitive
|
|
itemGroup.Add(new XElement(ns + "PackageReference",
|
|
new XAttribute("Include", "netstandard.Library"), new XAttribute("Version", "1.6.1")));
|
|
});
|
|
|
|
var buildCommand = new BuildCommand(testAsset);
|
|
|
|
buildCommand
|
|
.Execute()
|
|
.Should()
|
|
.Pass()
|
|
.And.HaveStdOutContaining("PackageReference")
|
|
.And.HaveStdOutContaining("'NETStandard.Library'");
|
|
}
|
|
|
|
[Fact]
|
|
public void ImplicitFrameworkReferencesAreOverriddenByProjectFile()
|
|
{
|
|
var testProject = new TestProject()
|
|
{
|
|
Name = "OverrideImplicitFrameworkReference",
|
|
TargetFrameworks = ToolsetInfo.CurrentTargetFramework,
|
|
};
|
|
|
|
var testAsset = _testAssetsManager.CreateTestProject(testProject)
|
|
.WithProjectChanges(project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
var itemGroup = new XElement(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
|
|
itemGroup.Add(new XElement(ns + "FrameworkReference",
|
|
new XAttribute("Include", "Microsoft.NETCore.App")));
|
|
});
|
|
|
|
var restoreCommand = new RestoreCommand(testAsset);
|
|
|
|
restoreCommand
|
|
.Execute()
|
|
.Should()
|
|
.Pass()
|
|
.And.HaveStdOutContaining("NETSDK1086");
|
|
|
|
var buildCommand = new BuildCommand(testAsset);
|
|
|
|
buildCommand
|
|
.Execute()
|
|
.Should()
|
|
.Pass()
|
|
.And.HaveStdOutContaining("NETSDK1086");
|
|
}
|
|
|
|
[Fact]
|
|
public void DuplicateFrameworkReferencesCauseError()
|
|
{
|
|
var testProject = new TestProject()
|
|
{
|
|
Name = "DuplicateFrameworkReference",
|
|
TargetFrameworks = ToolsetInfo.CurrentTargetFramework,
|
|
};
|
|
|
|
var testAsset = _testAssetsManager.CreateTestProject(testProject)
|
|
.WithProjectChanges(project =>
|
|
{
|
|
var ns = project.Root.Name.Namespace;
|
|
|
|
project.Root.Element(ns + "PropertyGroup").Add(
|
|
new XElement(ns + "DisableImplicitFrameworkReferences", "true"));
|
|
|
|
var itemGroup = new XElement(ns + "ItemGroup");
|
|
project.Root.Add(itemGroup);
|
|
|
|
itemGroup.Add(new XElement(ns + "FrameworkReference",
|
|
new XAttribute("Include", "Microsoft.NETCore.App")));
|
|
|
|
itemGroup.Add(new XElement(ns + "FrameworkReference",
|
|
new XAttribute("Include", "Microsoft.NETCore.App")));
|
|
});
|
|
|
|
var restoreCommand = new RestoreCommand(testAsset);
|
|
|
|
restoreCommand
|
|
.Execute()
|
|
.Should()
|
|
.Fail()
|
|
.And.HaveStdOutContaining("NETSDK1087");
|
|
}
|
|
|
|
[Theory]
|
|
[InlineData(false)]
|
|
[InlineData(true)]
|
|
public void Implicit_NetCoreApp_reference_can_be_overridden(bool disableImplicitFrameworkReferences)
|
|
{
|
|
var testProject = new TestProject()
|
|
{
|
|
Name = "OverrideNetCoreApp",
|
|
TargetFrameworks = "netcoreapp2.0",
|
|
IsExe = true
|
|
};
|
|
|
|
if (disableImplicitFrameworkReferences)
|
|
{
|
|
testProject.AdditionalProperties["DisableImplicitFrameworkReferences"] = "true";
|
|
}
|
|
|
|
string explicitPackageVersion = "2.0.3";
|
|
testProject.PackageReferences.Add(new TestPackageReference("Microsoft.NETCore.App", explicitPackageVersion));
|
|
|
|
var testAsset = _testAssetsManager.CreateTestProject(testProject, identifier: disableImplicitFrameworkReferences.ToString());
|
|
|
|
var buildCommand = new BuildCommand(testAsset);
|
|
|
|
buildCommand
|
|
.Execute()
|
|
.Should()
|
|
.Pass()
|
|
.And
|
|
.NotHaveStdOutContaining("NETSDK1071");
|
|
;
|
|
|
|
LockFile lockFile = LockFileUtilities.GetLockFile(Path.Combine(buildCommand.ProjectRootPath, "obj", "project.assets.json"), NullLogger.Instance);
|
|
|
|
var target = lockFile.GetTarget(NuGetFramework.Parse(testProject.TargetFrameworks), null);
|
|
var netCoreAppLibrary = target.Libraries.Single(l => l.Name == "Microsoft.NETCore.App");
|
|
netCoreAppLibrary.Version.ToString().Should().Be(explicitPackageVersion);
|
|
}
|
|
|
|
[Fact]
|
|
public void DuplicatePackageReferencesCanBeUsed()
|
|
{
|
|
var testProject = new TestProject()
|
|
{
|
|
Name = "DuplicatePackageReference",
|
|
TargetFrameworks = ToolsetInfo.CurrentTargetFramework,
|
|
};
|
|
|
|
testProject.PackageReferences.Add(new TestPackageReference("Newtonsoft.Json", ToolsetInfo.GetNewtonsoftJsonPackageVersion()));
|
|
testProject.PackageReferences.Add(new TestPackageReference("Newtonsoft.Json", ToolsetInfo.GetNewtonsoftJsonPackageVersion()));
|
|
|
|
testProject.SourceFiles["Test.cs"] = @"
|
|
public class Class1
|
|
{
|
|
public static void Test()
|
|
{
|
|
Newtonsoft.Json.Linq.JToken.Parse(""{ }"");
|
|
}
|
|
}";
|
|
|
|
var testAsset = _testAssetsManager.CreateTestProject(testProject);
|
|
|
|
var buildCommand = new BuildCommand(testAsset);
|
|
|
|
buildCommand
|
|
.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
// https://github.com/dotnet/sdk/issues/3027 could cause a situation where the build fails in VS
|
|
// but not the command line, apparently due to differences in how the different restores handle
|
|
// duplicate package references. So for this test, check the metadata.
|
|
|
|
var getValuesCommand = new GetValuesCommand(Log, Path.Combine(testAsset.TestRoot, testProject.Name),
|
|
testProject.TargetFrameworks, "PackageReference", GetValuesCommand.ValueType.Item);
|
|
|
|
getValuesCommand.MetadataNames.Add("PrivateAssets");
|
|
getValuesCommand.MetadataNames.Add("ExcludeAssets");
|
|
getValuesCommand.MetadataNames.Add("IsImplicitlyDefined");
|
|
|
|
getValuesCommand.Execute().Should().Pass();
|
|
|
|
var packageReferences = getValuesCommand.GetValuesWithMetadata();
|
|
|
|
var newtonsoftReferences = packageReferences.Where(pr => pr.value == "Newtonsoft.Json");
|
|
|
|
newtonsoftReferences.Count().Should().BeGreaterOrEqualTo(1);
|
|
|
|
foreach (var r in newtonsoftReferences)
|
|
{
|
|
r.metadata["PrivateAssets"].Should().BeEmpty();
|
|
r.metadata["ExcludeAssets"].Should().BeEmpty();
|
|
r.metadata["IsImplicitlyDefined"].Should().BeEmpty();
|
|
}
|
|
}
|
|
|
|
[Fact]
|
|
public void It_includes_Windows_App_SDK_items_in_the_correct_groups_if_Windows_App_SDK_is_present()
|
|
{
|
|
var testProject = new TestProject()
|
|
{
|
|
Name = "DontIncludeSourceFilesInNone",
|
|
TargetFrameworks = ToolsetInfo.CurrentTargetFramework,
|
|
IsExe = true,
|
|
};
|
|
|
|
// Windows App SDK
|
|
testProject.AdditionalProperties["EnableDefaultWindowsAppSdkContentItems"] = "true";
|
|
testProject.AdditionalProperties["EnableDefaultWindowsAppSdkPRIResourceItems"] = "true";
|
|
|
|
var testAsset = _testAssetsManager.CreateTestProject(testProject);
|
|
var projectFolder = Path.Combine(testAsset.TestRoot, testProject.Name);
|
|
|
|
File.WriteAllText(Path.Combine(projectFolder, "ResourcesResw.resw"), "<root/>");
|
|
string[] imageFiles = { "TestImage1.png", "TestImage2.bmp", "TestImage3.jpg", "TestImage4.dds", "TestImage5.tif", "TestImage6.tga", "TestImage7.gif" };
|
|
foreach (string fileName in imageFiles)
|
|
{
|
|
File.WriteAllText(Path.Combine(projectFolder, fileName), "");
|
|
}
|
|
|
|
// Validate None items.
|
|
var getNoneItemsCommand = new GetValuesCommand(Log, projectFolder, testProject.TargetFrameworks, "None", GetValuesCommand.ValueType.Item);
|
|
getNoneItemsCommand.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
getNoneItemsCommand.GetValues()
|
|
.Should()
|
|
.BeEmpty();
|
|
|
|
// Validate PRIResource items.
|
|
var getPRIResourceItemsCommand = new GetValuesCommand(Log, projectFolder, testProject.TargetFrameworks, "PRIResource", GetValuesCommand.ValueType.Item);
|
|
getPRIResourceItemsCommand.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
var getPRIResourceItems = getPRIResourceItemsCommand.GetValues();
|
|
getPRIResourceItems.Should().BeEquivalentTo(new[] { "ResourcesResw.resw" });
|
|
|
|
// Validate Content items.
|
|
var getContentItemsCommand = new GetValuesCommand(Log, projectFolder, testProject.TargetFrameworks, "Content", GetValuesCommand.ValueType.Item);
|
|
getContentItemsCommand.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
var getContentItems = getContentItemsCommand.GetValues();
|
|
getContentItems.Should().BeEquivalentTo(imageFiles);
|
|
}
|
|
|
|
[Fact]
|
|
public void It_does_not_include_Windows_App_SDK_items_if_Windows_App_SDK_is_absent()
|
|
{
|
|
var testProject = new TestProject()
|
|
{
|
|
Name = "DontIncludeSourceFilesInNone",
|
|
TargetFrameworks = ToolsetInfo.CurrentTargetFramework,
|
|
IsExe = true,
|
|
};
|
|
|
|
// Not setting the "EnableDefaultWindowsAppSdkContentItems" or "EnableDefaultWindowsAppSdkPRIResourceItems" properties!
|
|
|
|
var testAsset = _testAssetsManager.CreateTestProject(testProject);
|
|
var projectFolder = Path.Combine(testAsset.TestRoot, testProject.Name);
|
|
|
|
File.WriteAllText(Path.Combine(projectFolder, "ResourcesResw.resw"), "<root/>");
|
|
List<string> imageFiles = new() { "TestImage1.png", "TestImage2.bmp", "TestImage3.jpg", "TestImage4.dds", "TestImage5.tif", "TestImage6.tga", "TestImage7.gif" };
|
|
foreach (string fileName in imageFiles)
|
|
{
|
|
File.WriteAllText(Path.Combine(projectFolder, fileName), "");
|
|
}
|
|
|
|
// Validate None items.
|
|
var getNoneItemsCommand = new GetValuesCommand(Log, projectFolder, testProject.TargetFrameworks, "None", GetValuesCommand.ValueType.Item);
|
|
getNoneItemsCommand.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
var getNoneItems = getNoneItemsCommand.GetValues();
|
|
List<string> expectedFiles = imageFiles;
|
|
expectedFiles.Add("ResourcesResw.resw");
|
|
getNoneItems.Should().BeEquivalentTo(expectedFiles.ToArray());
|
|
|
|
// Validate PRIResource items.
|
|
var getPRIResourceItemsCommand = new GetValuesCommand(Log, projectFolder, testProject.TargetFrameworks, "PRIResource", GetValuesCommand.ValueType.Item);
|
|
getPRIResourceItemsCommand.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
getPRIResourceItemsCommand.GetValues()
|
|
.Should()
|
|
.BeEmpty();
|
|
|
|
// Validate Content items.
|
|
var getContentItemsCommand = new GetValuesCommand(Log, projectFolder, testProject.TargetFrameworks, "Content", GetValuesCommand.ValueType.Item);
|
|
getContentItemsCommand.Execute()
|
|
.Should()
|
|
.Pass();
|
|
|
|
getContentItemsCommand.GetValues()
|
|
.Should()
|
|
.BeEmpty();
|
|
}
|
|
|
|
void RemoveGeneratedCompileItems(List<string> compileItems)
|
|
{
|
|
// Remove auto-generated compile items.
|
|
// TargetFrameworkAttribute comes from %TEMP%\{TargetFrameworkMoniker}.AssemblyAttributes.cs
|
|
// Other default attributes generated by .NET SDK (for example AssemblyDescriptionAttribute and AssemblyTitleAttribute) come from
|
|
// { AssemblyName}.AssemblyInfo.cs in the intermediate output path
|
|
var itemsToRemove = compileItems.Where(i =>
|
|
i.EndsWith("AssemblyAttributes.cs", StringComparison.OrdinalIgnoreCase) ||
|
|
i.EndsWith("AssemblyInfo.cs", StringComparison.OrdinalIgnoreCase))
|
|
.ToList();
|
|
|
|
foreach (var itemToRemove in itemsToRemove)
|
|
{
|
|
compileItems.Remove(itemToRemove);
|
|
}
|
|
}
|
|
|
|
private void WriteFile(string path, string contents)
|
|
{
|
|
string folder = Path.GetDirectoryName(path);
|
|
Directory.CreateDirectory(folder);
|
|
File.WriteAllText(path, contents);
|
|
}
|
|
}
|
|
}
|