Skip to content

Commit

Permalink
Run dotnet info in the project output directory to ensure we are look…
Browse files Browse the repository at this point in the history
…ing in the correct SDK for the vstest console
  • Loading branch information
dibarbet committed Aug 4, 2023
1 parent c0e4fb4 commit b9a4f2b
Show file tree
Hide file tree
Showing 2 changed files with 9 additions and 7 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -18,25 +18,24 @@ internal sealed class DotnetCliHelper

private readonly ILogger _logger;
private readonly Lazy<string> _dotnetExecutablePath;
private readonly AsyncLazy<string> _dotnetSdkFolder;

[ImportingConstructor]
[Obsolete(MefConstruction.ImportingConstructorMessage, error: true)]
public DotnetCliHelper(ILoggerFactory loggerFactory)
{
_logger = loggerFactory.CreateLogger<DotnetCliHelper>();
_dotnetExecutablePath = new Lazy<string>(() => GetDotNetPathOrDefault());
_dotnetSdkFolder = new AsyncLazy<string>(GetDotnetSdkFolderFromDotnetExecutableAsync, cacheResult: true);
}

/// <summary>
/// The folder the dotnet executable is in could contain multiple SDK paths.
/// In order to figure out which one is the right one, we need to run dotnet --info
/// from the project directory (in order to respect any global.json that might be present)
/// which will output the correct SDK path.
/// </summary>
private async Task<string> GetDotnetSdkFolderFromDotnetExecutableAsync(CancellationToken cancellationToken)
private async Task<string> GetDotnetSdkFolderFromDotnetExecutableAsync(string projectOutputDirectory, CancellationToken cancellationToken)
{
using var process = Run("--info", workingDirectory: null, shouldLocalizeOutput: false);
using var process = Run("--info", workingDirectory: projectOutputDirectory, shouldLocalizeOutput: false);

string? dotnetSdkFolderPath = null;
process.OutputDataReceived += (_, e) =>
Expand Down Expand Up @@ -107,11 +106,12 @@ public Process Run(string arguments, string? workingDirectory, bool shouldLocali
return process;
}

public async Task<string> GetVsTestConsolePathAsync(CancellationToken cancellationToken)
public async Task<string> GetVsTestConsolePathAsync(string projectOutputDirectory, CancellationToken cancellationToken)
{
var dotnetSdkFolder = await _dotnetSdkFolder.GetValueAsync(cancellationToken);
var dotnetSdkFolder = await GetDotnetSdkFolderFromDotnetExecutableAsync(projectOutputDirectory, cancellationToken);
var vstestConsole = Path.Combine(dotnetSdkFolder, "vstest.console.dll");
Contract.ThrowIfFalse(File.Exists(vstestConsole), $"VSTestConsole was not found at {vstestConsole}");
_logger.LogDebug($"Using vstest console at {vstestConsole}");
return vstestConsole;
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -41,9 +41,11 @@ public async Task<RunTestsPartialResult[]> HandleRequestAsync(RunTestsParams req

var projectOutputPath = context.Document.Project.OutputFilePath;
Contract.ThrowIfFalse(File.Exists(projectOutputPath), $"Output path {projectOutputPath} is missing");
var projectOutputDirectory = Path.GetDirectoryName(projectOutputPath);
Contract.ThrowIfNull(projectOutputDirectory, $"Could not get project output directory from {projectOutputPath}");

// Find the appropriate vstest.console.dll from the SDK.
var vsTestConsolePath = await dotnetCliHelper.GetVsTestConsolePathAsync(cancellationToken);
var vsTestConsolePath = await dotnetCliHelper.GetVsTestConsolePathAsync(projectOutputDirectory, cancellationToken);

// Instantiate the test platform wrapper.
var vsTestConsoleWrapper = new VsTestConsoleWrapper(vsTestConsolePath, new ConsoleParameters
Expand Down

0 comments on commit b9a4f2b

Please sign in to comment.