Handle "runtimes" section (#4503)
* Migrate "runtimes" section as a RuntimeIdentifiers property in the resulting csproj file. Also do not call restore3 from publish3 anymore. * Fix up the publish3 tests to call restore3 first and the csproj files to have RuntimeIdentifiers
This commit is contained in:
parent
4aa1c1bfb4
commit
68afda8e4d
10 changed files with 183 additions and 37 deletions
|
@ -4,6 +4,7 @@
|
|||
<PropertyGroup>
|
||||
<OutputType>Exe</OutputType>
|
||||
<TargetFramework>netcoreapp1.0</TargetFramework>
|
||||
<RuntimeIdentifiers>win7-x64;win7-x86;osx.10.10-x64;osx.10.11-x64;ubuntu.14.04-x64;ubuntu.16.04-x64;centos.7-x64;rhel.7.2-x64;debian.8-x64;fedora.23-x64;opensuse.13.2-x64</RuntimeIdentifiers>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
|
|
|
@ -16,6 +16,7 @@ namespace Microsoft.DotNet.ProjectJsonMigration
|
|||
new MigrateJsonPropertiesRule(),
|
||||
new MigratePackOptionsRule(),
|
||||
new MigrateRuntimeOptionsRule(),
|
||||
new MigrateRuntimesRule(),
|
||||
new MigratePublishOptionsRule(),
|
||||
new MigrateProjectDependenciesRule(),
|
||||
new MigratePackageDependenciesAndToolsRule(),
|
||||
|
|
|
@ -0,0 +1,35 @@
|
|||
// Copyright (c) .NET Foundation and contributors. All rights reserved.
|
||||
// Licensed under the MIT license. See LICENSE file in the project root for full license information.
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Microsoft.DotNet.ProjectJsonMigration.Transforms;
|
||||
|
||||
namespace Microsoft.DotNet.ProjectJsonMigration.Rules
|
||||
{
|
||||
public class MigrateRuntimesRule : IMigrationRule
|
||||
{
|
||||
AddPropertyTransform<IList<string>> RuntimeIdentifiersTransform =>
|
||||
new AddPropertyTransform<IList<string>>(
|
||||
"RuntimeIdentifiers",
|
||||
l => String.Join(";", l),
|
||||
l => l.Count > 0);
|
||||
|
||||
private readonly ITransformApplicator _transformApplicator;
|
||||
|
||||
public MigrateRuntimesRule(ITransformApplicator transformApplicator = null)
|
||||
{
|
||||
_transformApplicator = transformApplicator ?? new TransformApplicator();
|
||||
}
|
||||
|
||||
public void Apply(MigrationSettings migrationSettings, MigrationRuleInputs migrationRuleInputs)
|
||||
{
|
||||
var propertyGroup = migrationRuleInputs.CommonPropertyGroup;
|
||||
|
||||
_transformApplicator.Execute(
|
||||
RuntimeIdentifiersTransform.Transform(migrationRuleInputs.DefaultProjectContext.ProjectFile.Runtimes),
|
||||
propertyGroup,
|
||||
mergeExisting: true);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -71,6 +71,8 @@ namespace Microsoft.DotNet.ProjectModel
|
|||
|
||||
public RuntimeOptions RuntimeOptions { get; set; }
|
||||
|
||||
public IList<string> Runtimes { get; set; }
|
||||
|
||||
public IDictionary<string, string> Commands { get; } = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
|
||||
|
||||
public IDictionary<string, IEnumerable<string>> Scripts { get; } = new Dictionary<string, IEnumerable<string>>(StringComparer.OrdinalIgnoreCase);
|
||||
|
|
|
@ -159,6 +159,7 @@ namespace Microsoft.DotNet.ProjectModel
|
|||
|
||||
project.Dependencies = new List<ProjectLibraryDependency>();
|
||||
project.Tools = new List<ProjectLibraryDependency>();
|
||||
project.Runtimes = new List<string>();
|
||||
|
||||
// Project files
|
||||
project.Files = new ProjectFilesCollection(rawProject, project.ProjectDirectory, project.ProjectFilePath);
|
||||
|
@ -224,6 +225,8 @@ namespace Microsoft.DotNet.ProjectModel
|
|||
"tools",
|
||||
isGacOrFrameworkReference: false);
|
||||
|
||||
PopulateRuntimes(project.Runtimes, rawProject);
|
||||
|
||||
JToken runtimeOptionsToken;
|
||||
if (rawProject.TryGetValue("runtimeOptions", out runtimeOptionsToken))
|
||||
{
|
||||
|
@ -370,6 +373,21 @@ namespace Microsoft.DotNet.ProjectModel
|
|||
}
|
||||
}
|
||||
|
||||
private static void PopulateRuntimes(IList<string> results, JObject settings)
|
||||
{
|
||||
var runtimes = settings.Value<JToken>("runtimes") as JObject;
|
||||
if (runtimes != null)
|
||||
{
|
||||
foreach (var runtime in runtimes)
|
||||
{
|
||||
if (!string.IsNullOrEmpty(runtime.Key))
|
||||
{
|
||||
results.Add(runtime.Key);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void BuildTargetFrameworksAndConfigurations(Project project, JObject projectJsonObject)
|
||||
{
|
||||
// Get the shared compilationOptions
|
||||
|
|
|
@ -25,12 +25,6 @@ namespace Microsoft.DotNet.Tools.Publish3
|
|||
|
||||
public int Execute()
|
||||
{
|
||||
int restoreResult = EnsureRestored();
|
||||
if (restoreResult != 0)
|
||||
{
|
||||
throw new GracefulException("Restore failed. Please fix the errors and try publishing again.");
|
||||
}
|
||||
|
||||
List<string> msbuildArgs = new List<string>();
|
||||
|
||||
if (!string.IsNullOrEmpty(ProjectPath))
|
||||
|
@ -70,19 +64,5 @@ namespace Microsoft.DotNet.Tools.Publish3
|
|||
return new MSBuildForwardingApp(msbuildArgs).Execute();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Ensures that the project has been restored for the specified runtime.
|
||||
/// </summary>
|
||||
private int EnsureRestored()
|
||||
{
|
||||
int result = 0;
|
||||
|
||||
if (!string.IsNullOrEmpty(Runtime))
|
||||
{
|
||||
result = Restore3Command.Run(new[] { $"/p:RuntimeIdentifiers={Runtime}" });
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,79 @@
|
|||
using Microsoft.Build.Construction;
|
||||
using Microsoft.DotNet.ProjectJsonMigration;
|
||||
using Microsoft.DotNet.ProjectModel;
|
||||
using Microsoft.DotNet.Tools.Test.Utilities;
|
||||
using NuGet.Frameworks;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using Xunit;
|
||||
using FluentAssertions;
|
||||
using Microsoft.DotNet.ProjectJsonMigration.Rules;
|
||||
|
||||
namespace Microsoft.DotNet.ProjectJsonMigration.Tests
|
||||
{
|
||||
public class GivenThatIWantToMigrateRuntimes : TestBase
|
||||
{
|
||||
[Fact]
|
||||
public void It_migrates_runtimes()
|
||||
{
|
||||
var projectJson = @"
|
||||
{
|
||||
""runtimes"": {
|
||||
""win7-x64"": { },
|
||||
""win7-x86"": { },
|
||||
""osx.10.10-x64"": { }
|
||||
}
|
||||
}
|
||||
";
|
||||
|
||||
var testDirectory = Temp.CreateDirectory().Path;
|
||||
var migratedProj = TemporaryProjectFileRuleRunner.RunRules(new IMigrationRule[]
|
||||
{
|
||||
new MigrateRuntimesRule()
|
||||
}, projectJson, testDirectory);
|
||||
|
||||
migratedProj.Properties.Count(p => p.Name == "RuntimeIdentifiers").Should().Be(1);
|
||||
migratedProj.Properties.First(p => p.Name == "RuntimeIdentifiers").Value
|
||||
.Should().Be("win7-x64;win7-x86;osx.10.10-x64");
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void It_has_an_empty_runtime_node_to_migrate()
|
||||
{
|
||||
var projectJson = @"
|
||||
{
|
||||
""runtimes"": {
|
||||
}
|
||||
}
|
||||
";
|
||||
|
||||
var testDirectory = Temp.CreateDirectory().Path;
|
||||
var migratedProj = TemporaryProjectFileRuleRunner.RunRules(new IMigrationRule[]
|
||||
{
|
||||
new MigrateRuntimesRule()
|
||||
}, projectJson, testDirectory);
|
||||
|
||||
migratedProj.Properties.Count(p => p.Name == "RuntimeIdentifiers").Should().Be(0);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void It_has_no_runtimes_to_migrate()
|
||||
{
|
||||
var projectJson = @"
|
||||
{
|
||||
}
|
||||
";
|
||||
|
||||
var testDirectory = Temp.CreateDirectory().Path;
|
||||
var migratedProj = TemporaryProjectFileRuleRunner.RunRules(new IMigrationRule[]
|
||||
{
|
||||
new MigrateRuntimesRule()
|
||||
}, projectJson, testDirectory);
|
||||
|
||||
migratedProj.Properties.Count(p => p.Name == "RuntimeIdentifiers").Should().Be(0);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -29,13 +29,13 @@ namespace Microsoft.DotNet.Tools.Test.Utilities
|
|||
|
||||
public override CommandResult Execute(string args = "")
|
||||
{
|
||||
args = $"publish3 {args} {BuildArgs()}";
|
||||
args = $"publish3 {BuildArgs()} {args} ";
|
||||
return base.Execute(args);
|
||||
}
|
||||
|
||||
public override CommandResult ExecuteWithCapturedOutput(string args = "")
|
||||
{
|
||||
args = $"publish3 {args} {BuildArgs()}";
|
||||
args = $"publish3 {BuildArgs()} {args}";
|
||||
return base.ExecuteWithCapturedOutput(args);
|
||||
}
|
||||
|
||||
|
|
|
@ -10,8 +10,8 @@ using System.IO;
|
|||
using Microsoft.DotNet.Tools.Migrate;
|
||||
using Build3Command = Microsoft.DotNet.Tools.Test.Utilities.Build3Command;
|
||||
using BuildCommand = Microsoft.DotNet.Tools.Test.Utilities.BuildCommand;
|
||||
using Publish3Command = Microsoft.DotNet.Tools.Test.Utilities.Publish3Command;
|
||||
using System.Runtime.Loader;
|
||||
using Newtonsoft.Json;
|
||||
using Newtonsoft.Json.Linq;
|
||||
|
||||
namespace Microsoft.DotNet.Migration.Tests
|
||||
|
@ -346,6 +346,19 @@ namespace Microsoft.DotNet.Migration.Tests
|
|||
result.StdErr.Should().Contain("Migration failed.");
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void It_migrates_and_publishes_projects_with_runtimes()
|
||||
{
|
||||
var projectName = "TestAppSimple";
|
||||
var projectDirectory = TestAssetsManager.CreateTestInstance(projectName, callingMethod: "i")
|
||||
.WithLockFiles()
|
||||
.Path;
|
||||
|
||||
CleanBinObj(projectDirectory);
|
||||
BuildProjectJsonMigrateBuildMSBuild(projectDirectory, projectName);
|
||||
PublishMSBuild(projectDirectory, projectName, "win7-x64");
|
||||
}
|
||||
|
||||
[WindowsOnlyTheory]
|
||||
[InlineData("DesktopTestProjects", "AutoAddDesktopReferencesDuringMigrate", true)]
|
||||
[InlineData("TestProjects", "TestAppSimple", false)]
|
||||
|
@ -558,6 +571,25 @@ namespace Microsoft.DotNet.Migration.Tests
|
|||
return result.StdOut;
|
||||
}
|
||||
|
||||
private string PublishMSBuild(string projectDirectory, string projectName, string runtime, string configuration = "Debug")
|
||||
{
|
||||
if (projectName != null)
|
||||
{
|
||||
projectName = projectName + ".csproj";
|
||||
}
|
||||
|
||||
DeleteXproj(projectDirectory);
|
||||
|
||||
var result = new Publish3Command()
|
||||
.WithRuntime(runtime)
|
||||
.WithWorkingDirectory(projectDirectory)
|
||||
.ExecuteWithCapturedOutput($"{projectName} /p:Configuration={configuration}");
|
||||
|
||||
result.Should().Pass();
|
||||
|
||||
return result.StdOut;
|
||||
}
|
||||
|
||||
private void DeleteXproj(string projectDirectory)
|
||||
{
|
||||
var xprojFiles = Directory.EnumerateFiles(projectDirectory, "*.xproj");
|
||||
|
|
|
@ -25,24 +25,20 @@ namespace Microsoft.DotNet.Cli.Publish3.Tests
|
|||
new Restore3Command()
|
||||
.WithWorkingDirectory(testProjectDirectory)
|
||||
.Execute()
|
||||
.Should()
|
||||
.Pass();
|
||||
.Should().Pass();
|
||||
|
||||
new Publish3Command()
|
||||
.WithWorkingDirectory(testProjectDirectory)
|
||||
.Execute("--framework netcoreapp1.0")
|
||||
.Should()
|
||||
.Pass();
|
||||
.Should().Pass();
|
||||
|
||||
var configuration = Environment.GetEnvironmentVariable("CONFIGURATION") ?? "Debug";
|
||||
var outputDll = Path.Combine(testProjectDirectory, "bin", configuration, "netcoreapp1.0", "publish", $"{testAppName}.dll");
|
||||
|
||||
new TestCommand("dotnet")
|
||||
.ExecuteWithCapturedOutput(outputDll)
|
||||
.Should()
|
||||
.Pass()
|
||||
.And
|
||||
.HaveStdOutContaining("Hello World");
|
||||
.Should().Pass()
|
||||
.And.HaveStdOutContaining("Hello World");
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
@ -55,23 +51,25 @@ namespace Microsoft.DotNet.Cli.Publish3.Tests
|
|||
var testProjectDirectory = testInstance.TestRoot;
|
||||
var rid = DotnetLegacyRuntimeIdentifiers.InferLegacyRestoreRuntimeIdentifier();
|
||||
|
||||
new Restore3Command()
|
||||
.WithWorkingDirectory(testProjectDirectory)
|
||||
.Execute()
|
||||
.Should().Pass();
|
||||
|
||||
new Publish3Command()
|
||||
.WithFramework("netcoreapp1.0")
|
||||
.WithRuntime(rid)
|
||||
.WithWorkingDirectory(testProjectDirectory)
|
||||
.Execute()
|
||||
.Should()
|
||||
.Pass();
|
||||
.Should().Pass();
|
||||
|
||||
var configuration = Environment.GetEnvironmentVariable("CONFIGURATION") ?? "Debug";
|
||||
var outputProgram = Path.Combine(testProjectDirectory, "bin", configuration, "netcoreapp1.0", rid, "publish", $"{testAppName}{Constants.ExeSuffix}");
|
||||
|
||||
new TestCommand(outputProgram)
|
||||
.ExecuteWithCapturedOutput()
|
||||
.Should()
|
||||
.Pass()
|
||||
.And
|
||||
.HaveStdOutContaining("Hello World");
|
||||
.Should().Pass()
|
||||
.And.HaveStdOutContaining("Hello World");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue