diff --git a/Microsoft.DotNet.Cli.sln b/Microsoft.DotNet.Cli.sln
index 4343cabcc..be6b9bf42 100644
--- a/Microsoft.DotNet.Cli.sln
+++ b/Microsoft.DotNet.Cli.sln
@@ -221,6 +221,8 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "templates", "templates", "{
build\templates\templates.csproj = build\templates\templates.csproj
EndProjectSection
EndProject
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "dotnet-back-compat.Tests", "test\dotnet-back-compat.Tests\dotnet-back-compat.Tests.csproj", "{A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}"
+EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@@ -1509,6 +1511,30 @@ Global
{CACA427D-5A71-45E6-88DC-3E2DB6C4D52D}.RelWithDebInfo|x64.Build.0 = Release|Any CPU
{CACA427D-5A71-45E6-88DC-3E2DB6C4D52D}.RelWithDebInfo|x86.ActiveCfg = Release|Any CPU
{CACA427D-5A71-45E6-88DC-3E2DB6C4D52D}.RelWithDebInfo|x86.Build.0 = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Debug|x64.ActiveCfg = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Debug|x64.Build.0 = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Debug|x86.ActiveCfg = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Debug|x86.Build.0 = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.MinSizeRel|Any CPU.ActiveCfg = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.MinSizeRel|Any CPU.Build.0 = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.MinSizeRel|x64.ActiveCfg = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.MinSizeRel|x64.Build.0 = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.MinSizeRel|x86.ActiveCfg = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.MinSizeRel|x86.Build.0 = Debug|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Release|Any CPU.Build.0 = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Release|x64.ActiveCfg = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Release|x64.Build.0 = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Release|x86.ActiveCfg = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.Release|x86.Build.0 = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.RelWithDebInfo|Any CPU.ActiveCfg = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.RelWithDebInfo|Any CPU.Build.0 = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.RelWithDebInfo|x64.ActiveCfg = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.RelWithDebInfo|x64.Build.0 = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.RelWithDebInfo|x86.ActiveCfg = Release|Any CPU
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6}.RelWithDebInfo|x86.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
@@ -1577,5 +1603,6 @@ Global
{CACA427D-5A71-45E6-88DC-3E2DB6C4D52D} = {17735A9D-BFD9-4585-A7CB-3208CA6EA8A7}
{3275D006-54C8-4C64-A537-B9941C5D2F0C} = {89905EC4-BC0F-443B-8ADF-691321F10108}
{DE4D1AEB-871B-4E7C-945A-453F9A490C06} = {89905EC4-BC0F-443B-8ADF-691321F10108}
+ {A4C198B4-D46E-4CA8-87DF-B2B206DCCAE6} = {17735A9D-BFD9-4585-A7CB-3208CA6EA8A7}
EndGlobalSection
EndGlobal
diff --git a/src/dotnet/commands/dotnet-migrate/MigrateCommandParser.cs b/src/dotnet/commands/dotnet-migrate/MigrateCommandParser.cs
index f5f5c771f..f878b67f2 100644
--- a/src/dotnet/commands/dotnet-migrate/MigrateCommandParser.cs
+++ b/src/dotnet/commands/dotnet-migrate/MigrateCommandParser.cs
@@ -29,15 +29,19 @@ namespace Microsoft.DotNet.Cli
description: LocalizableStrings.CmdProjectArgumentDescription),
CommonOptions.HelpOption(),
Create.Option("-t|--template-file",
- LocalizableStrings.CmdTemplateDescription),
+ LocalizableStrings.CmdTemplateDescription,
+ Accept.ExactlyOneArgument()),
Create.Option("-v|--sdk-package-version",
- LocalizableStrings.CmdVersionDescription),
+ LocalizableStrings.CmdVersionDescription,
+ Accept.ExactlyOneArgument()),
Create.Option("-x|--xproj-file",
- LocalizableStrings.CmdXprojFileDescription),
+ LocalizableStrings.CmdXprojFileDescription,
+ Accept.ExactlyOneArgument()),
Create.Option("-s|--skip-project-references",
LocalizableStrings.CmdSkipProjectReferencesDescription),
Create.Option("-r|--report-file",
- LocalizableStrings.CmdReportFileDescription),
+ LocalizableStrings.CmdReportFileDescription,
+ Accept.ExactlyOneArgument()),
Create.Option("--format-report-file-json",
LocalizableStrings.CmdReportOutputDescription),
Create.Option("--skip-backup",
diff --git a/test/Microsoft.DotNet.Cli.Tests.sln b/test/Microsoft.DotNet.Cli.Tests.sln
index f6e479323..30e4e2f60 100644
--- a/test/Microsoft.DotNet.Cli.Tests.sln
+++ b/test/Microsoft.DotNet.Cli.Tests.sln
@@ -74,6 +74,8 @@ Project("{13B669BE-BB05-4DDF-9536-439F39A36129}") = "dotnet-add-package.Tests",
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "dotnet-store.Tests", "dotnet-store.Tests\dotnet-store.Tests.csproj", "{04B21F0F-E645-44E3-868B-3C97E435FB74}"
EndProject
+Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "dotnet-back-compat.Tests", "dotnet-back-compat.Tests\dotnet-back-compat.Tests.csproj", "{27351B2F-325B-4843-9F4C-BC53FD06A7B5}"
+EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
@@ -480,6 +482,30 @@ Global
{04B21F0F-E645-44E3-868B-3C97E435FB74}.Release|x64.Build.0 = Release|Any CPU
{04B21F0F-E645-44E3-868B-3C97E435FB74}.Release|x86.ActiveCfg = Release|Any CPU
{04B21F0F-E645-44E3-868B-3C97E435FB74}.Release|x86.Build.0 = Release|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Debug|x64.ActiveCfg = Debug|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Debug|x64.Build.0 = Debug|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Debug|x86.ActiveCfg = Debug|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Debug|x86.Build.0 = Debug|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Release|Any CPU.Build.0 = Release|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Release|x64.ActiveCfg = Release|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Release|x64.Build.0 = Release|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Release|x86.ActiveCfg = Release|Any CPU
+ {7CA9ECD0-9284-496B-890F-94B63ECB37EC}.Release|x86.Build.0 = Release|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Debug|Any CPU.Build.0 = Debug|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Debug|x64.ActiveCfg = Debug|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Debug|x64.Build.0 = Debug|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Debug|x86.ActiveCfg = Debug|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Debug|x86.Build.0 = Debug|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Release|Any CPU.ActiveCfg = Release|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Release|Any CPU.Build.0 = Release|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Release|x64.ActiveCfg = Release|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Release|x64.Build.0 = Release|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Release|x86.ActiveCfg = Release|Any CPU
+ {27351B2F-325B-4843-9F4C-BC53FD06A7B5}.Release|x86.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
diff --git a/test/dotnet-back-compat.Tests/GivenThatWeWantToBeBackwardsCompatibleWith1xProjects.cs b/test/dotnet-back-compat.Tests/GivenThatWeWantToBeBackwardsCompatibleWith1xProjects.cs
new file mode 100644
index 000000000..e104f4abf
--- /dev/null
+++ b/test/dotnet-back-compat.Tests/GivenThatWeWantToBeBackwardsCompatibleWith1xProjects.cs
@@ -0,0 +1,93 @@
+// 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.IO;
+using FluentAssertions;
+using Microsoft.DotNet.Tools.Test.Utilities;
+using Xunit;
+using System.Linq;
+using System.Xml.Linq;
+
+namespace Microsoft.DotNet.Cli.Build.Tests
+{
+ public class GivenThatWeWantToBeBackwardsCompatibleWith1xProjects : TestBase
+ {
+ [Theory]
+ [InlineData("netcoreapp1.0")]
+ [InlineData("netcoreapp1.1")]
+ public void ItRestoresBuildsAndRuns(string target)
+ {
+
+ var testAppName = "TestAppSimple";
+ var testInstance = TestAssets.Get(testAppName)
+ .CreateInstance(testAppName + "_" + target.Replace('.', '_'))
+ .WithSourceFiles();
+
+ // Replace the 'TargetFramework'
+ ChangeProjectTargetFramework(testInstance.Root.GetFile($"{testAppName}.csproj"), target);
+
+ new RestoreCommand()
+ .WithWorkingDirectory(testInstance.Root)
+ .Execute()
+ .Should().Pass();
+
+ new BuildCommand()
+ .WithWorkingDirectory(testInstance.Root)
+ .Execute()
+ .Should().Pass();
+
+ var configuration = Environment.GetEnvironmentVariable("CONFIGURATION") ?? "Debug";
+
+ var outputDll = testInstance.Root.GetDirectory("bin", configuration, target)
+ .GetFile($"{testAppName}.dll");
+
+ new DotnetCommand()
+ .ExecuteWithCapturedOutput(outputDll.FullName)
+ .Should().Pass()
+ .And.HaveStdOutContaining("Hello World");
+ }
+
+ [Theory]
+ [InlineData("netstandard1.3")]
+ [InlineData("netstandard1.6")]
+ public void ItRestoresBuildsAndPacks(string target)
+ {
+
+ var testAppName = "TestAppSimple";
+ var testInstance = TestAssets.Get(testAppName)
+ .CreateInstance(testAppName + "_" + target.Replace('.', '_'))
+ .WithSourceFiles();
+
+ // Replace the 'TargetFramework'
+ ChangeProjectTargetFramework(testInstance.Root.GetFile($"{testAppName}.csproj"), target);
+
+ new RestoreCommand()
+ .WithWorkingDirectory(testInstance.Root)
+ .Execute()
+ .Should().Pass();
+
+ new BuildCommand()
+ .WithWorkingDirectory(testInstance.Root)
+ .Execute()
+ .Should().Pass();
+
+ new PackCommand()
+ .WithWorkingDirectory(testInstance.Root)
+ .Execute()
+ .Should().Pass();
+ }
+
+
+ void ChangeProjectTargetFramework(FileInfo projectFile, string target)
+ {
+ var projectXml = XDocument.Load(projectFile.ToString());
+ var ns = projectXml.Root.Name.Namespace;
+ var propertyGroup = projectXml.Root.Elements(ns + "PropertyGroup").First();
+ var rootNamespaceElement = propertyGroup.Element(ns + "TargetFramework");
+ rootNamespaceElement.SetValue(target);
+ projectXml.Save(projectFile.ToString());
+ }
+
+ }
+}
diff --git a/test/dotnet-back-compat.Tests/dotnet-back-compat.Tests.csproj b/test/dotnet-back-compat.Tests/dotnet-back-compat.Tests.csproj
new file mode 100644
index 000000000..0b7b9fa26
--- /dev/null
+++ b/test/dotnet-back-compat.Tests/dotnet-back-compat.Tests.csproj
@@ -0,0 +1,20 @@
+
+
+
+
+ $(CliTargetFramework)
+ $(CLI_SharedFrameworkVersion)
+ true
+ dotnet-back-compat.Tests
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/test/dotnet.Tests/ParserTests/MigrateParserTests.cs b/test/dotnet.Tests/ParserTests/MigrateParserTests.cs
new file mode 100644
index 000000000..814333dd0
--- /dev/null
+++ b/test/dotnet.Tests/ParserTests/MigrateParserTests.cs
@@ -0,0 +1,58 @@
+// 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.Linq;
+using FluentAssertions;
+using Microsoft.DotNet.Cli.CommandLine;
+using Microsoft.DotNet.Tools.Migrate;
+using Xunit;
+using Xunit.Abstractions;
+using Parser = Microsoft.DotNet.Cli.Parser;
+
+namespace Microsoft.DotNet.Tests.ParserTests
+{
+ public class MigrateParserTests
+ {
+ public MigrateParserTests(ITestOutputHelper output)
+ {
+ this.output = output;
+ }
+
+ private readonly ITestOutputHelper output;
+
+ [Fact]
+ public void MigrateParserConstructMigrateCommandWithoutError()
+ {
+ var command = Parser.Instance;
+
+ var result = command.Parse("dotnet migrate --skip-backup -s " +
+ "-x \"C:\\ConsoleAppOnCore_1\\ConsoleAppOnCore_1.xproj\" " +
+ "\"C:\\ConsoleAppOnCore_1\\project.json\" " +
+ "-r \"C:\\report.wfw\" " +
+ "--format-report-file-json");
+
+ Action a = () => result["dotnet"]["migrate"].Value();
+ a.ShouldNotThrow();
+ }
+
+ [Fact]
+ public void MigrateParseGetResultCorrectlyAsFollowing()
+ {
+ var command = Parser.Instance;
+
+ var result = command.Parse("dotnet migrate --skip-backup -s " +
+ "-x \"C:\\ConsoleAppOnCore_1\\ConsoleAppOnCore_1.xproj\" " +
+ "\"C:\\ConsoleAppOnCore_1\\project.json\" " +
+ "-r \"C:\\report.wfw\" " +
+ "--format-report-file-json");
+
+ result["dotnet"]["migrate"]["skip-backup"].Value().Should().BeTrue();
+ result["dotnet"]["migrate"]["skip-project-references"].Value().Should().BeTrue();
+ result["dotnet"]["migrate"]["format-report-file-json"].Value().Should().BeTrue();
+ result["dotnet"]["migrate"]["xproj-file"].Value().Should().Be("C:\\ConsoleAppOnCore_1\\ConsoleAppOnCore_1.xproj");
+ result["dotnet"]["migrate"]["report-file"].Value().Should().Be("C:\\report.wfw");
+ result["dotnet"]["migrate"].Arguments.Contains("C:\\ConsoleAppOnCore_1\\project.json").Should().BeTrue();
+ }
+ }
+}
\ No newline at end of file