align code in dotnet-run (#2679)

we used to use different code when --framework was specified than when it was not specified, this synchronizes them to use the same code path which removes a hidden NullRef

also adds tests to cover both cases
This commit is contained in:
Andrew Stanton-Nurse 2016-04-25 13:53:02 -07:00
parent 06f57c5c81
commit a729b97b35
5 changed files with 44 additions and 78 deletions

View file

@ -171,9 +171,7 @@ namespace Microsoft.DotNet.ProjectModel
EmptyArray<ProjectContext>.Value;
}
public ProjectContext GetProjectContext(string projectPath, NuGetFramework framework) => GetProjectContext(projectPath, framework, EmptyArray<string>.Value);
public ProjectContext GetProjectContext(string projectPath, NuGetFramework framework, IEnumerable<string> runtimeIdentifier)
public ProjectContext GetProjectContext(string projectPath, NuGetFramework framework)
{
var contexts = GetProjectContextCollection(projectPath);
if (contexts == null)
@ -183,11 +181,16 @@ namespace Microsoft.DotNet.ProjectModel
return contexts
.ProjectContexts
.FirstOrDefault(c => Equals(c.TargetFramework, framework) && RidsMatch(c.RuntimeIdentifier, runtimeIdentifier));
.FirstOrDefault(c => Equals(c.TargetFramework, framework) && string.IsNullOrEmpty(c.RuntimeIdentifier));
}
public ProjectContext GetRuntimeContext(ProjectContext context, IEnumerable<string> runtimeIdentifiers)
{
if(!runtimeIdentifiers.Any())
{
return context;
}
var contexts = GetProjectContextCollection(context.ProjectDirectory);
if (contexts == null)
{
@ -515,11 +518,5 @@ namespace Microsoft.DotNet.ProjectModel
yield return description;
}
}
private static bool RidsMatch(string rid, IEnumerable<string> compatibleRids)
{
return (string.IsNullOrEmpty(rid) && !compatibleRids.Any()) ||
(compatibleRids.Contains(rid));
}
}
}

View file

@ -20,6 +20,13 @@ namespace Microsoft.DotNet.Tools.Run
public string Project = null;
public IReadOnlyList<string> Args = null;
public static readonly string[] DefaultFrameworks = new[]
{
FrameworkConstants.FrameworkIdentifiers.NetCoreApp,
FrameworkConstants.FrameworkIdentifiers.NetStandardApp,
};
ProjectContext _context;
List<string> _args;
private WorkspaceContext _workspace;
@ -61,41 +68,38 @@ namespace Microsoft.DotNet.Tools.Run
Configuration = Constants.DefaultConfiguration;
}
var frameworkContexts = _workspace.GetProjectContexts(Project).Where(c => string.IsNullOrEmpty(c.RuntimeIdentifier));
var frameworkContexts = _workspace.GetProjectContextCollection(Project).FrameworkOnlyContexts;
var rids = PlatformServices.Default.Runtime.GetAllCandidateRuntimeIdentifiers();
ProjectContext frameworkContext;
if (Framework == null)
{
var defaultFrameworks = new[]
{
FrameworkConstants.FrameworkIdentifiers.NetCoreApp,
FrameworkConstants.FrameworkIdentifiers.NetStandardApp,
};
ProjectContext context;
if (frameworkContexts.Count() == 1)
{
context = frameworkContexts.Single();
frameworkContext = frameworkContexts.Single();
}
else
{
context = frameworkContexts.FirstOrDefault(c => defaultFrameworks.Contains(c.TargetFramework.Framework));
if (context == null)
{
throw new InvalidOperationException($"Couldn't find target to run. Possible causes:" + Environment.NewLine +
"1. No project.lock.json file or restore failed - run `dotnet restore`" + Environment.NewLine +
$"2. project.lock.json has multiple targets none of which is in default list ({string.Join(", ", defaultFrameworks)})");
}
frameworkContext = frameworkContexts.FirstOrDefault(c => DefaultFrameworks.Contains(c.TargetFramework.Framework));
}
_context = _workspace.GetRuntimeContext(context, rids);
}
else
{
_context = _workspace.GetProjectContext(Project, NuGetFramework.Parse(Framework), rids);
frameworkContext = frameworkContexts.FirstOrDefault(c => Equals(c.TargetFramework, NuGetFramework.Parse(Framework)));
}
if (frameworkContext == null)
{
throw new InvalidOperationException($"Couldn't find target to run. Possible causes:" + Environment.NewLine +
"1. No project.lock.json file or restore failed - run `dotnet restore`" + Environment.NewLine +
Framework == null ?
$"2. project.lock.json has multiple targets none of which is in default list ({string.Join(", ", DefaultFrameworks)})" :
$"2. The project does not support the desired framework: {Framework}");
}
_context = _workspace.GetRuntimeContext(frameworkContext, rids);
if (Args == null)
{
_args = new List<string>();

View file

@ -14,50 +14,15 @@ namespace Microsoft.DotNet.Tools.Test.Utilities
private bool _preserveTemporary;
private string _appArgs;
private string ProjectPathOption
{
get
{
return _projectPath == string.Empty ?
"" :
$"-p \"{_projectPath}\"";
}
}
private string ProjectPathOption => string.IsNullOrEmpty(_projectPath) ? "" : $"-p \"{_projectPath}\"";
private string FrameworkOption
{
get
{
return _framework == string.Empty ?
"" :
$"-f {_framework}";
}
}
private string FrameworkOption => string.IsNullOrEmpty(_framework) ? "" : $"-f {_framework}";
private string ConfigurationOption
{
get
{
return _configuration == string.Empty ?
"" :
$"-c {_configuration}";
}
}
private string ConfigurationOption => string.IsNullOrEmpty(_configuration) ? "" : $"-c {_configuration}";
private string PreserveTemporaryOption
{
get
{
return _preserveTemporary ?
$"-t \"{_projectPath}\"" :
"";
}
}
private string PreserveTemporaryOption => _preserveTemporary ? $"-t \"{_projectPath}\"" : "";
private string AppArgsArgument
{
get { return _appArgs; }
}
private string AppArgsArgument => _appArgs;
public RunCommand(
string projectPath,
@ -92,9 +57,6 @@ namespace Microsoft.DotNet.Tools.Test.Utilities
return base.ExecuteAsync(args);
}
private string BuildArgs()
{
return $"{ProjectPathOption} {FrameworkOption} {ConfigurationOption} {PreserveTemporaryOption} {AppArgsArgument}";
}
private string BuildArgs() => $"{ProjectPathOption} {FrameworkOption} {ConfigurationOption} {PreserveTemporaryOption} {AppArgsArgument}";
}
}

View file

@ -220,7 +220,8 @@ namespace Microsoft.DotNet.Tools.Compiler.Tests
}
var workspace = WorkspaceContext.Create(ProjectReaderSettings.ReadFromEnvironment(), designTime: false);
var context = workspace.GetProjectContext(projectJson, TestAssetFramework, rids);
var context = workspace.GetRuntimeContext(workspace.GetProjectContext(projectJson, TestAssetFramework), rids);
context = workspace.GetRuntimeContext(context, rids);
managedCompiler.Compile(context, _args);
RuntimeOutputDir = Path.Combine(OutputPath, rid);

View file

@ -89,9 +89,11 @@ namespace Microsoft.DotNet.Tools.Publish.Tests
}
[WindowsOnlyTheory]
[InlineData("KestrelDesktop", "http://localhost:20301")]
[InlineData("KestrelDesktopWithRuntimes", "http://localhost:20302")]
public async Task DesktopApp_WithKestrel_WorksWhenRun(string project, string url)
[InlineData("KestrelDesktop", "http://localhost:20301", null)]
[InlineData("KestrelDesktopWithRuntimes", "http://localhost:20302", null)]
[InlineData("KestrelDesktop", "http://localhost:20303", "net451")]
[InlineData("KestrelDesktopWithRuntimes", "http://localhost:20304", "net451")]
public async Task DesktopApp_WithKestrel_WorksWhenRun(string project, string url, string framework)
{
// Disabled due to https://github.com/dotnet/cli/issues/2428
if (RuntimeInformation.ProcessArchitecture == Architecture.X86)
@ -104,7 +106,7 @@ namespace Microsoft.DotNet.Tools.Publish.Tests
.WithBuildArtifacts();
Task exec = null;
var command = new RunCommand(Path.Combine(testInstance.TestRoot, project));
var command = new RunCommand(Path.Combine(testInstance.TestRoot, project), framework);
try
{
exec = command.ExecuteAsync(url);