post migration cleanup (#4449)
* Create tests * Basic scenario working & tested * Feature Complete * prevent build of intentionally broken test asset * Update migrate command backup * PR Feedback * Move negative test to negative test directory * Fix tests * make test output directories unique * Merge Conflict * make backup the default behavior * Pass2Fail * Remove tests' PJ dependency
This commit is contained in:
parent
a4776a2b2c
commit
5ede3b6367
14 changed files with 376 additions and 19 deletions
|
@ -0,0 +1,17 @@
|
||||||
|
// 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.Diagnostics;
|
||||||
|
|
||||||
|
namespace TestApp
|
||||||
|
{
|
||||||
|
public class Program
|
||||||
|
{
|
||||||
|
public static int Main(string[] args)
|
||||||
|
{
|
||||||
|
Console.WriteLine(TestLibrary.Helper.GetMessage());
|
||||||
|
return 100;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,30 @@
|
||||||
|
{
|
||||||
|
"version": "1.0.0-*",
|
||||||
|
"buildOptions": {
|
||||||
|
"emitEntryPoint": true,
|
||||||
|
"preserveCompilationContext": true
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"TestLibrary": {
|
||||||
|
"target": "project",
|
||||||
|
"version": "1.0.0-*"
|
||||||
|
},
|
||||||
|
"Microsoft.NETCore.App": "1.0.1"
|
||||||
|
},
|
||||||
|
"frameworks": {
|
||||||
|
"netcoreapp1.0": {}
|
||||||
|
},
|
||||||
|
"runtimes": {
|
||||||
|
"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": {}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,24 @@
|
||||||
|
// 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;
|
||||||
|
|
||||||
|
namespace TestLibrary
|
||||||
|
{
|
||||||
|
public static class Helper
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Gets the message from the helper. This comment is here to help test XML documentation file generation, please do not remove it.
|
||||||
|
/// </summary>
|
||||||
|
/// <returns>A message</returns>
|
||||||
|
public static string GetMessage()
|
||||||
|
{
|
||||||
|
return "This string came from the test library!";
|
||||||
|
}
|
||||||
|
|
||||||
|
public static void SayHi()
|
||||||
|
{
|
||||||
|
Console.WriteLine("Hello there!");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,22 @@
|
||||||
|
{
|
||||||
|
"version": "1.0.0-*",
|
||||||
|
"buildOptions": {
|
||||||
|
"nowarn": [
|
||||||
|
"CS1591"
|
||||||
|
],
|
||||||
|
"xmlDoc": true,
|
||||||
|
"additionalArguments": [
|
||||||
|
"-highentropyva+"
|
||||||
|
]
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"MissingP2PDependency": {
|
||||||
|
"target": "project",
|
||||||
|
"version": "1.0.0-*"
|
||||||
|
},
|
||||||
|
"NETStandard.Library": "1.6.0"
|
||||||
|
},
|
||||||
|
"frameworks": {
|
||||||
|
"netstandard1.5": {}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,3 @@
|
||||||
|
{
|
||||||
|
"projects": [ "."]
|
||||||
|
}
|
|
@ -11,12 +11,15 @@ using Microsoft.Build.Evaluation;
|
||||||
using Microsoft.DotNet.Cli.Utils;
|
using Microsoft.DotNet.Cli.Utils;
|
||||||
using Microsoft.DotNet.ProjectJsonMigration;
|
using Microsoft.DotNet.ProjectJsonMigration;
|
||||||
using Microsoft.DotNet.Internal.ProjectModel;
|
using Microsoft.DotNet.Internal.ProjectModel;
|
||||||
using ProjectModel = Microsoft.DotNet.Internal.ProjectModel.Project;
|
using Project = Microsoft.DotNet.Internal.ProjectModel.Project;
|
||||||
|
using Microsoft.DotNet.Tools.Common;
|
||||||
|
|
||||||
namespace Microsoft.DotNet.Tools.Migrate
|
namespace Microsoft.DotNet.Tools.Migrate
|
||||||
{
|
{
|
||||||
public partial class MigrateCommand
|
public partial class MigrateCommand
|
||||||
{
|
{
|
||||||
|
private readonly DirectoryInfo _workspaceDirectory;
|
||||||
|
private readonly DirectoryInfo _backupDirectory;
|
||||||
private readonly string _templateFile;
|
private readonly string _templateFile;
|
||||||
private readonly string _projectArg;
|
private readonly string _projectArg;
|
||||||
private readonly string _sdkVersion;
|
private readonly string _sdkVersion;
|
||||||
|
@ -24,6 +27,7 @@ namespace Microsoft.DotNet.Tools.Migrate
|
||||||
private readonly bool _skipProjectReferences;
|
private readonly bool _skipProjectReferences;
|
||||||
private readonly string _reportFile;
|
private readonly string _reportFile;
|
||||||
private readonly bool _reportFormatJson;
|
private readonly bool _reportFormatJson;
|
||||||
|
private readonly bool _skipBackup;
|
||||||
|
|
||||||
public MigrateCommand(
|
public MigrateCommand(
|
||||||
string templateFile,
|
string templateFile,
|
||||||
|
@ -32,15 +36,21 @@ namespace Microsoft.DotNet.Tools.Migrate
|
||||||
string xprojFilePath,
|
string xprojFilePath,
|
||||||
string reportFile,
|
string reportFile,
|
||||||
bool skipProjectReferences,
|
bool skipProjectReferences,
|
||||||
bool reportFormatJson)
|
bool reportFormatJson,
|
||||||
{
|
bool skipBackup)
|
||||||
|
{
|
||||||
_templateFile = templateFile;
|
_templateFile = templateFile;
|
||||||
_projectArg = projectArg ?? Directory.GetCurrentDirectory();
|
_projectArg = projectArg ?? Directory.GetCurrentDirectory();
|
||||||
|
_workspaceDirectory = File.Exists(_projectArg)
|
||||||
|
? new FileInfo(_projectArg).Directory
|
||||||
|
: new DirectoryInfo(_projectArg);
|
||||||
|
_backupDirectory = new DirectoryInfo(Path.Combine(_workspaceDirectory.FullName, "backup"));
|
||||||
_sdkVersion = sdkVersion;
|
_sdkVersion = sdkVersion;
|
||||||
_xprojFilePath = xprojFilePath;
|
_xprojFilePath = xprojFilePath;
|
||||||
_skipProjectReferences = skipProjectReferences;
|
_skipProjectReferences = skipProjectReferences;
|
||||||
_reportFile = reportFile;
|
_reportFile = reportFile;
|
||||||
_reportFormatJson = reportFormatJson;
|
_reportFormatJson = reportFormatJson;
|
||||||
|
_skipBackup = skipBackup;
|
||||||
}
|
}
|
||||||
|
|
||||||
public int Execute()
|
public int Execute()
|
||||||
|
@ -82,12 +92,73 @@ namespace Microsoft.DotNet.Tools.Migrate
|
||||||
|
|
||||||
temporaryDotnetNewProject.Clean();
|
temporaryDotnetNewProject.Clean();
|
||||||
|
|
||||||
|
MoveProjectJsonArtifactsToBackup(migrationReport);
|
||||||
|
|
||||||
return migrationReport.FailedProjectsCount;
|
return migrationReport.FailedProjectsCount;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void MoveProjectJsonArtifactsToBackup(MigrationReport migrationReport)
|
||||||
|
{
|
||||||
|
if (_skipBackup)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (migrationReport.FailedProjectsCount > 0)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
BackupGlobalJson();
|
||||||
|
|
||||||
|
BackupProjects(migrationReport);
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private void BackupGlobalJson()
|
||||||
|
{
|
||||||
|
_backupDirectory.Create();
|
||||||
|
|
||||||
|
var globalJson = Path.Combine(_workspaceDirectory.FullName, GlobalSettings.FileName);
|
||||||
|
|
||||||
|
if (File.Exists(globalJson))
|
||||||
|
{
|
||||||
|
File.Move(globalJson, Path.Combine(_backupDirectory.FullName, GlobalSettings.FileName));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void BackupProjects(MigrationReport migrationReport)
|
||||||
|
{
|
||||||
|
foreach (var report in migrationReport.ProjectMigrationReports)
|
||||||
|
{
|
||||||
|
MigrateProject(report);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private void MigrateProject(ProjectMigrationReport report)
|
||||||
|
{
|
||||||
|
var projectDirectory = PathUtility.EnsureTrailingSlash(report.ProjectDirectory);
|
||||||
|
|
||||||
|
var relativeDirectory = PathUtility.GetRelativePath(PathUtility.EnsureTrailingSlash(_workspaceDirectory.FullName), projectDirectory);
|
||||||
|
|
||||||
|
var targetDirectory = String.IsNullOrEmpty(relativeDirectory)
|
||||||
|
? _backupDirectory.FullName
|
||||||
|
: Path.Combine(_backupDirectory.FullName, relativeDirectory);
|
||||||
|
|
||||||
|
PathUtility.EnsureDirectory(PathUtility.EnsureTrailingSlash(targetDirectory));
|
||||||
|
|
||||||
|
var movableFiles = new DirectoryInfo(projectDirectory)
|
||||||
|
.EnumerateFiles()
|
||||||
|
.Where(f => f.Name == Project.FileName || f.Extension == ".xproj");
|
||||||
|
|
||||||
|
foreach (var movableFile in movableFiles)
|
||||||
|
{
|
||||||
|
movableFile.MoveTo(Path.Combine(targetDirectory, movableFile.Name));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private void WriteReport(MigrationReport migrationReport)
|
private void WriteReport(MigrationReport migrationReport)
|
||||||
{
|
{
|
||||||
|
|
||||||
if (!string.IsNullOrEmpty(_reportFile))
|
if (!string.IsNullOrEmpty(_reportFile))
|
||||||
{
|
{
|
||||||
using (var outputTextWriter = GetReportFileOutputTextWriter())
|
using (var outputTextWriter = GetReportFileOutputTextWriter())
|
||||||
|
@ -194,13 +265,14 @@ namespace Microsoft.DotNet.Tools.Migrate
|
||||||
{
|
{
|
||||||
IEnumerable<string> projects = null;
|
IEnumerable<string> projects = null;
|
||||||
|
|
||||||
if (projectArg.EndsWith(ProjectModel.FileName, StringComparison.OrdinalIgnoreCase))
|
if (projectArg.EndsWith(Project.FileName, StringComparison.OrdinalIgnoreCase))
|
||||||
{
|
{
|
||||||
projects = Enumerable.Repeat(projectArg, 1);
|
projects = Enumerable.Repeat(projectArg, 1);
|
||||||
}
|
}
|
||||||
else if (projectArg.EndsWith(GlobalSettings.FileName, StringComparison.OrdinalIgnoreCase))
|
else if (projectArg.EndsWith(GlobalSettings.FileName, StringComparison.OrdinalIgnoreCase))
|
||||||
{
|
{
|
||||||
projects = GetProjectsFromGlobalJson(projectArg);
|
projects = GetProjectsFromGlobalJson(projectArg);
|
||||||
|
|
||||||
if (!projects.Any())
|
if (!projects.Any())
|
||||||
{
|
{
|
||||||
throw new Exception("Unable to find any projects in global.json");
|
throw new Exception("Unable to find any projects in global.json");
|
||||||
|
@ -208,8 +280,8 @@ namespace Microsoft.DotNet.Tools.Migrate
|
||||||
}
|
}
|
||||||
else if (Directory.Exists(projectArg))
|
else if (Directory.Exists(projectArg))
|
||||||
{
|
{
|
||||||
projects =
|
projects = Directory.EnumerateFiles(projectArg, Project.FileName, SearchOption.AllDirectories);
|
||||||
Directory.EnumerateFiles(projectArg, ProjectModel.FileName, SearchOption.AllDirectories);
|
|
||||||
if (!projects.Any())
|
if (!projects.Any())
|
||||||
{
|
{
|
||||||
throw new Exception($"No project.json file found in '{projectArg}'");
|
throw new Exception($"No project.json file found in '{projectArg}'");
|
||||||
|
|
|
@ -42,7 +42,8 @@ namespace Microsoft.DotNet.Tools.Migrate
|
||||||
CommandOption skipProjectReferences = app.Option("-s|--skip-project-references", "Skip migrating project references. By default project references are migrated recursively", CommandOptionType.BoolValue);
|
CommandOption skipProjectReferences = app.Option("-s|--skip-project-references", "Skip migrating project references. By default project references are migrated recursively", CommandOptionType.BoolValue);
|
||||||
|
|
||||||
CommandOption reportFile = app.Option("-r|--report-file", "Output migration report to a file in addition to the console.", CommandOptionType.SingleValue);
|
CommandOption reportFile = app.Option("-r|--report-file", "Output migration report to a file in addition to the console.", CommandOptionType.SingleValue);
|
||||||
CommandOption structuredReportOutput = app.Option("--format-report-file-json", "Output migration report file as json rather than user messages", CommandOptionType.BoolValue);
|
CommandOption structuredReportOutput = app.Option("--format-report-file-json", "Output migration report file as json rather than user messages", CommandOptionType.BoolValue);
|
||||||
|
CommandOption skipBackup = app.Option("--skip-backup", "Skip moving project.json, global.json, and *.xproj to a `backup` directory after successful migration.", CommandOptionType.BoolValue);
|
||||||
|
|
||||||
app.OnExecute(() =>
|
app.OnExecute(() =>
|
||||||
{
|
{
|
||||||
|
@ -53,7 +54,8 @@ namespace Microsoft.DotNet.Tools.Migrate
|
||||||
xprojFile.Value(),
|
xprojFile.Value(),
|
||||||
reportFile.Value(),
|
reportFile.Value(),
|
||||||
skipProjectReferences.BoolValue.HasValue ? skipProjectReferences.BoolValue.Value : false,
|
skipProjectReferences.BoolValue.HasValue ? skipProjectReferences.BoolValue.Value : false,
|
||||||
structuredReportOutput.BoolValue.HasValue ? structuredReportOutput.BoolValue.Value : false);
|
structuredReportOutput.BoolValue.HasValue ? structuredReportOutput.BoolValue.Value : false,
|
||||||
|
skipBackup.BoolValue.HasValue ? skipBackup.BoolValue.Value : false);
|
||||||
|
|
||||||
return migrateCommand.Execute();
|
return migrateCommand.Execute();
|
||||||
});
|
});
|
||||||
|
|
|
@ -21,7 +21,7 @@ namespace Microsoft.DotNet.ProjectJsonMigration.Tests
|
||||||
public GivenThatIWantToMigrateAssemblyInfo()
|
public GivenThatIWantToMigrateAssemblyInfo()
|
||||||
{
|
{
|
||||||
var projectDirectory =
|
var projectDirectory =
|
||||||
TestAssetsManager.CreateTestInstance("AppWithAssemblyInfo", callingMethod: "i").Path;
|
TestAssetsManager.CreateTestInstance("AppWithAssemblyInfo").Path;
|
||||||
var projectContext =
|
var projectContext =
|
||||||
ProjectContext.Create(projectDirectory, FrameworkConstants.CommonFrameworks.NetCoreApp10);
|
ProjectContext.Create(projectDirectory, FrameworkConstants.CommonFrameworks.NetCoreApp10);
|
||||||
_mockProject = ProjectRootElement.Create();
|
_mockProject = ProjectRootElement.Create();
|
||||||
|
|
|
@ -30,11 +30,31 @@ namespace Microsoft.DotNet.Tools.Test.Utilities
|
||||||
return new AndConstraint<DirectoryInfoAssertions>(this);
|
return new AndConstraint<DirectoryInfoAssertions>(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
public AndConstraint<DirectoryInfoAssertions> HaveFile(string expectedFile)
|
public AndConstraint<DirectoryInfoAssertions> HaveFile(string expectedFile, string because = "", params object[] reasonArgs)
|
||||||
{
|
{
|
||||||
var file = _dirInfo.EnumerateFiles(expectedFile, SearchOption.TopDirectoryOnly).SingleOrDefault();
|
var file = _dirInfo.EnumerateFiles(expectedFile, SearchOption.TopDirectoryOnly).SingleOrDefault();
|
||||||
Execute.Assertion.ForCondition(file != null)
|
|
||||||
.FailWith("Expected File {0} cannot be found in directory {1}.", expectedFile, _dirInfo.FullName);
|
Execute.Assertion
|
||||||
|
.ForCondition(file != null)
|
||||||
|
.BecauseOf(because, reasonArgs)
|
||||||
|
.FailWith($"Expected File {expectedFile} cannot be found in directory {_dirInfo.FullName}.");
|
||||||
|
|
||||||
|
return new AndConstraint<DirectoryInfoAssertions>(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
public AndConstraint<DirectoryInfoAssertions> HaveTextFile(string expectedFile, string expectedContents, string because = "", params object[] reasonArgs)
|
||||||
|
{
|
||||||
|
this.HaveFile(expectedFile, because, reasonArgs);
|
||||||
|
|
||||||
|
var file = _dirInfo.EnumerateFiles(expectedFile, SearchOption.TopDirectoryOnly).SingleOrDefault();
|
||||||
|
|
||||||
|
var contents = File.ReadAllText(file.FullName);
|
||||||
|
|
||||||
|
Execute.Assertion
|
||||||
|
.ForCondition(contents.Equals(expectedContents))
|
||||||
|
.BecauseOf(because, reasonArgs)
|
||||||
|
.FailWith($"Expected file {expectedFile} to contain \n\n{expectedContents}\n\nbut it contains\n\n{contents}\n");
|
||||||
|
|
||||||
return new AndConstraint<DirectoryInfoAssertions>(this);
|
return new AndConstraint<DirectoryInfoAssertions>(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -56,12 +76,26 @@ namespace Microsoft.DotNet.Tools.Test.Utilities
|
||||||
return new AndConstraint<DirectoryInfoAssertions>(this);
|
return new AndConstraint<DirectoryInfoAssertions>(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
public AndConstraint<DirectoryInfoAssertions> HaveFilesMatching(string expectedFilesSearchPattern, SearchOption searchOption)
|
public AndConstraint<DirectoryInfoAssertions> HaveTextFiles(IDictionary<string, string> expectedFiles, string because = "", params object[] reasonArgs)
|
||||||
|
{
|
||||||
|
foreach (var expectedFile in expectedFiles)
|
||||||
|
{
|
||||||
|
HaveTextFile(expectedFile.Key, expectedFile.Value, because, reasonArgs);
|
||||||
|
}
|
||||||
|
|
||||||
|
return new AndConstraint<DirectoryInfoAssertions>(this);
|
||||||
|
}
|
||||||
|
|
||||||
|
public AndConstraint<DirectoryInfoAssertions> HaveFilesMatching(string expectedFilesSearchPattern, SearchOption searchOption, string because = "", params object[] reasonArgs)
|
||||||
{
|
{
|
||||||
var matchingFileExists = _dirInfo.EnumerateFiles(expectedFilesSearchPattern, searchOption).Any();
|
var matchingFileExists = _dirInfo.EnumerateFiles(expectedFilesSearchPattern, searchOption).Any();
|
||||||
Execute.Assertion.ForCondition(matchingFileExists == true)
|
|
||||||
|
Execute.Assertion
|
||||||
|
.ForCondition(matchingFileExists == true)
|
||||||
|
.BecauseOf(because, reasonArgs)
|
||||||
.FailWith("Expected directory {0} to contain files matching {1}, but no matching file exists.",
|
.FailWith("Expected directory {0} to contain files matching {1}, but no matching file exists.",
|
||||||
_dirInfo.FullName, expectedFilesSearchPattern);
|
_dirInfo.FullName, expectedFilesSearchPattern);
|
||||||
|
|
||||||
return new AndConstraint<DirectoryInfoAssertions>(this);
|
return new AndConstraint<DirectoryInfoAssertions>(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -108,5 +142,15 @@ namespace Microsoft.DotNet.Tools.Test.Utilities
|
||||||
|
|
||||||
return new AndConstraint<DirectoryInfoAssertions>(this);
|
return new AndConstraint<DirectoryInfoAssertions>(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public AndConstraint<DirectoryInfoAssertions> NotExist(string because = "", params object[] reasonArgs)
|
||||||
|
{
|
||||||
|
Execute.Assertion
|
||||||
|
.ForCondition(_dirInfo.Exists == false)
|
||||||
|
.BecauseOf(because, reasonArgs)
|
||||||
|
.FailWith($"Expected directory {_dirInfo.FullName} to not exist, but it does.");
|
||||||
|
|
||||||
|
return new AndConstraint<DirectoryInfoAssertions>(this);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,29 @@
|
||||||
|
// 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 Microsoft.DotNet.Cli.Utils;
|
||||||
|
|
||||||
|
namespace Microsoft.DotNet.Tools.Test.Utilities
|
||||||
|
{
|
||||||
|
public sealed class MigrateCommand : TestCommand
|
||||||
|
{
|
||||||
|
public MigrateCommand()
|
||||||
|
: base("dotnet")
|
||||||
|
{
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
public override CommandResult Execute(string args="")
|
||||||
|
{
|
||||||
|
args = $"migrate {args}";
|
||||||
|
|
||||||
|
return base.Execute(args);
|
||||||
|
}
|
||||||
|
|
||||||
|
public override CommandResult ExecuteWithCapturedOutput(string args = "")
|
||||||
|
{
|
||||||
|
args = $"migrate {args}";
|
||||||
|
return base.ExecuteWithCapturedOutput(args);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
111
test/dotnet-migrate.Tests/GivenThatAnAppWasMigrated.cs
Normal file
111
test/dotnet-migrate.Tests/GivenThatAnAppWasMigrated.cs
Normal file
|
@ -0,0 +1,111 @@
|
||||||
|
using FluentAssertions;
|
||||||
|
using Microsoft.DotNet.TestFramework;
|
||||||
|
using Microsoft.DotNet.Tools.Common;
|
||||||
|
using Microsoft.DotNet.Tools.Test.Utilities;
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.IO;
|
||||||
|
using Xunit;
|
||||||
|
|
||||||
|
namespace Microsoft.DotNet.Migration.Tests
|
||||||
|
{
|
||||||
|
public class GivenThatAnAppWasMigrated : TestBase
|
||||||
|
{
|
||||||
|
[Theory]
|
||||||
|
[InlineData("PJTestAppSimple")]
|
||||||
|
[InlineData("TestAppWithLibrary")]
|
||||||
|
public void When_migration_succeeds_Then_project_json_artifacts_get_moved_to_backup(string testProjectName)
|
||||||
|
{
|
||||||
|
var testRoot = TestAssetsManager
|
||||||
|
.CreateTestInstance(testProjectName, identifier: testProjectName)
|
||||||
|
.Path;
|
||||||
|
|
||||||
|
var backupRoot = Path.Combine(testRoot, "backup");
|
||||||
|
|
||||||
|
var migratableArtifacts = GetProjectJsonArtifacts(testRoot);
|
||||||
|
|
||||||
|
new MigrateCommand()
|
||||||
|
.WithWorkingDirectory(testRoot)
|
||||||
|
.Execute()
|
||||||
|
.Should().Pass();
|
||||||
|
|
||||||
|
var backupArtifacts = GetProjectJsonArtifacts(backupRoot);
|
||||||
|
|
||||||
|
backupArtifacts.Should().Equal(migratableArtifacts, "Because all of and only these artifacts should have been moved");
|
||||||
|
|
||||||
|
new DirectoryInfo(testRoot).Should().NotHaveFiles(backupArtifacts.Keys);
|
||||||
|
|
||||||
|
new DirectoryInfo(backupRoot).Should().HaveTextFiles(backupArtifacts);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Theory]
|
||||||
|
[InlineData("TestAppWithLibraryAndMissingP2P")]
|
||||||
|
public void When_migration_fails_Then_project_json_artifacts_do_not_get_moved_to_backup(string testProjectName)
|
||||||
|
{
|
||||||
|
var testRoot = new TestAssetsManager(Path.Combine(RepoRoot, "TestAssets", "NonRestoredTestProjects"))
|
||||||
|
.CreateTestInstance(testProjectName, identifier: testProjectName)
|
||||||
|
.Path;
|
||||||
|
|
||||||
|
var backupRoot = Path.Combine(testRoot, "backup");
|
||||||
|
|
||||||
|
var migratableArtifacts = GetProjectJsonArtifacts(testRoot);
|
||||||
|
|
||||||
|
new MigrateCommand()
|
||||||
|
.WithWorkingDirectory(testRoot)
|
||||||
|
.Execute()
|
||||||
|
.Should().Fail();
|
||||||
|
|
||||||
|
new DirectoryInfo(backupRoot).Should().NotExist("Because migration failed and therefore no backup is needed.");
|
||||||
|
|
||||||
|
new DirectoryInfo(testRoot).Should().HaveTextFiles(migratableArtifacts, "Because migration failed so nothing was moved to backup.");
|
||||||
|
}
|
||||||
|
|
||||||
|
[Theory]
|
||||||
|
[InlineData("PJTestAppSimple")]
|
||||||
|
public void When_skipbackup_specified_Then_project_json_artifacts_do_not_get_moved_to_backup(string testProjectName)
|
||||||
|
{
|
||||||
|
var testRoot = TestAssetsManager.CreateTestInstance(testProjectName, identifier: testProjectName).Path;
|
||||||
|
|
||||||
|
var backupRoot = Path.Combine(testRoot, "backup");
|
||||||
|
|
||||||
|
var migratableArtifacts = GetProjectJsonArtifacts(testRoot);
|
||||||
|
|
||||||
|
new MigrateCommand()
|
||||||
|
.WithWorkingDirectory(testRoot)
|
||||||
|
.Execute("--skip-backup")
|
||||||
|
.Should().Pass();
|
||||||
|
|
||||||
|
new DirectoryInfo(backupRoot).Should().NotExist("Because --skip-backup was specified.");
|
||||||
|
|
||||||
|
new DirectoryInfo(testRoot).Should().HaveTextFiles(migratableArtifacts, "Because --skip-backup was specified.");
|
||||||
|
}
|
||||||
|
|
||||||
|
private Dictionary<string, string> GetProjectJsonArtifacts(string rootPath)
|
||||||
|
{
|
||||||
|
var catalog = new Dictionary<string, string>();
|
||||||
|
|
||||||
|
var patterns = new [] { "global.json", "project.json", "*.xproj" };
|
||||||
|
|
||||||
|
foreach (var pattern in patterns)
|
||||||
|
{
|
||||||
|
AddArtifactsToCatalog(catalog, rootPath, pattern);
|
||||||
|
}
|
||||||
|
|
||||||
|
return catalog;
|
||||||
|
}
|
||||||
|
|
||||||
|
private void AddArtifactsToCatalog(Dictionary<string, string> catalog, string basePath, string pattern)
|
||||||
|
{
|
||||||
|
basePath = PathUtility.EnsureTrailingSlash(basePath);
|
||||||
|
|
||||||
|
var baseDirectory = new DirectoryInfo(basePath);
|
||||||
|
|
||||||
|
var files = baseDirectory.GetFiles(pattern, SearchOption.AllDirectories);
|
||||||
|
|
||||||
|
foreach (var file in files)
|
||||||
|
{
|
||||||
|
catalog.Add(PathUtility.GetRelativePath(basePath, file.FullName), File.ReadAllText(file.FullName));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -12,6 +12,8 @@ using BuildCommand = Microsoft.DotNet.Tools.Test.Utilities.BuildCommand;
|
||||||
using System.Runtime.Loader;
|
using System.Runtime.Loader;
|
||||||
using Newtonsoft.Json.Linq;
|
using Newtonsoft.Json.Linq;
|
||||||
|
|
||||||
|
using MigrateCommand = Microsoft.DotNet.Tools.Migrate.MigrateCommand;
|
||||||
|
|
||||||
namespace Microsoft.DotNet.Migration.Tests
|
namespace Microsoft.DotNet.Migration.Tests
|
||||||
{
|
{
|
||||||
public class GivenThatIWantToMigrateTestApps : TestBase
|
public class GivenThatIWantToMigrateTestApps : TestBase
|
||||||
|
@ -354,9 +356,10 @@ namespace Microsoft.DotNet.Migration.Tests
|
||||||
public void It_migrates_and_publishes_projects_with_runtimes()
|
public void It_migrates_and_publishes_projects_with_runtimes()
|
||||||
{
|
{
|
||||||
var projectName = "PJTestAppSimple";
|
var projectName = "PJTestAppSimple";
|
||||||
var projectDirectory = TestAssetsManager.CreateTestInstance(projectName, callingMethod: "i")
|
var projectDirectory = TestAssetsManager
|
||||||
.WithLockFiles()
|
.CreateTestInstance(projectName)
|
||||||
.Path;
|
.WithLockFiles()
|
||||||
|
.Path;
|
||||||
|
|
||||||
CleanBinObj(projectDirectory);
|
CleanBinObj(projectDirectory);
|
||||||
BuildProjectJsonMigrateBuildMSBuild(projectDirectory, projectName);
|
BuildProjectJsonMigrateBuildMSBuild(projectDirectory, projectName);
|
||||||
|
@ -440,7 +443,7 @@ namespace Microsoft.DotNet.Migration.Tests
|
||||||
|
|
||||||
private void VerifyMigration(IEnumerable<string> expectedProjects, string rootDir)
|
private void VerifyMigration(IEnumerable<string> expectedProjects, string rootDir)
|
||||||
{
|
{
|
||||||
var migratedProjects = Directory.EnumerateFiles(rootDir, "project.json", SearchOption.AllDirectories)
|
var migratedProjects = Directory.EnumerateFiles(rootDir, "*.csproj", SearchOption.AllDirectories)
|
||||||
.Where(s => Directory.EnumerateFiles(Path.GetDirectoryName(s), "*.csproj").Count() == 1)
|
.Where(s => Directory.EnumerateFiles(Path.GetDirectoryName(s), "*.csproj").Count() == 1)
|
||||||
.Where(s => Path.GetFileName(Path.GetDirectoryName(s)).Contains("Project"))
|
.Where(s => Path.GetFileName(Path.GetDirectoryName(s)).Contains("Project"))
|
||||||
.Select(s => Path.GetFileName(Path.GetDirectoryName(s)));
|
.Select(s => Path.GetFileName(Path.GetDirectoryName(s)));
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue