Cake: The MSTest tool doesn't pick up the mstest.exe from Visual Studio 2017

Created on 7 Mar 2017  Â·  19Comments  Â·  Source: cake-build/cake

What You Are Seeing?

I run the unit tests like this:

MSTest("./src/**/bin/" + configuration + "/*.Tests.dll");

I get the following error when running the build script:

An error occurred when executing task 'Run-Unit-Tests'.
Error: MSTest: Could not locate executable.

What is Expected?

I expect my unit tests to run.

What version of Cake are you using?

0.17

Are you running on a 32 or 64 bit system?

64 bit

What environment are you running on? Windows? Linux? Mac?

Windows 10

Are you running on a CI Server? If so, which one?

No, just building on my local machine.

How Did You Get This To Happen? (Steps to Reproduce)

Run a build with unit tests on a machine with only Visual Studio 2017 (Community Edition).

Output Log

========================================
Run-Unit-Tests
========================================
Executing task: Run-Unit-Tests
An error occurred when executing task 'Run-Unit-Tests'.
Error: Cake.Core.CakeException: MSTest: Could not locate executable.
   at Cake.Core.Tooling.Tool`1.RunProcess(TSettings settings, ProcessArgumentBuilder arguments, ProcessSettings processSettings)
   at Cake.Core.Tooling.Tool`1.Run(TSettings settings, ProcessArgumentBuilder arguments, ProcessSettings processSettings, Action`1 postAction)
   at Cake.Core.Tooling.Tool`1.Run(TSettings settings, ProcessArgumentBuilder arguments)
   at Cake.Common.Tools.MSTest.MSTestRunner.Run(IEnumerable`1 assemblyPaths, MSTestSettings settings)
   at Cake.Common.Tools.MSTest.MSTestAliases.MSTest(ICakeContext context, IEnumerable`1 assemblyPaths, MSTestSettings settings)
   at Cake.Common.Tools.MSTest.MSTestAliases.MSTest(ICakeContext context, IEnumerable`1 assemblyPaths)
   at Cake.Common.Tools.MSTest.MSTestAliases.MSTest(ICakeContext context, String pattern)
   at Submission#0.<.ctor>b__11()
   at Cake.Core.CakeTaskBuilderExtensions.<>c__DisplayClass5_0.<Does>b__0(ICakeContext context)
   at Cake.Core.ActionTask.Execute(ICakeContext context)
   at Cake.Core.DefaultExecutionStrategy.Execute(CakeTask task, ICakeContext context)
   at Cake.Core.CakeEngine.ExecuteTask(ICakeContext context, IExecutionStrategy strategy, Stopwatch stopWatch, CakeTask task, CakeReport report)
   at Cake.Core.CakeEngine.RunTarget(ICakeContext context, IExecutionStrategy strategy, String target)
   at Cake.Scripting.BuildScriptHost.RunTarget(String target)
   at Submission#0..ctor(Session session, Object& submissionResult)
   at Submission#0.<Factory>(Session session)
   at Roslyn.Scripting.CommonScriptEngine.Execute[T](String code, String path, DiagnosticBag diagnostics, Session session, Boolean isInteractive)
   at Roslyn.Scripting.Session.Execute(String code)
   at Cake.Scripting.Roslyn.Stable.DefaultRoslynScriptSession.Execute(Script script)
   at Cake.Core.Scripting.ScriptRunner.Run(IScriptHost host, FilePath scriptPath, IDictionary`2 arguments)
   at Cake.Commands.BuildCommand.Execute(CakeOptions options)
   at Cake.CakeApplication.Run(CakeOptions options)
   at Cake.Program.Main()
Improvement

Most helpful comment

Looking forward to the fix. This is the workaround I've been using:

// https://github.com/cake-build/cake/issues/1522
VSTestSettings FixToolPath(VSTestSettings settings)
{
    #tool vswhere
    settings.ToolPath =
        VSWhereLatest(new VSWhereLatestSettings { Requires = "Microsoft.VisualStudio.PackageGroup.TestTools.Core" })
        .CombineWithFilePath(File(@"Common7\IDE\CommonExtensions\Microsoft\TestWindow\vstest.console.exe"));
    return settings;
}

Then just wrap your settings:

VSTest("**/*.Tests.dll", FixToolPath(new VSTestSettings { Foo = 42 }))

(See https://github.com/Microsoft/vswhere/wiki/Find-VSTest.)

All 19 comments

I already had a peek in the source code and saw this piece of code in MSTest\MSTestRunner.cs:

private FilePath GetToolPath(string version)
{
    var programFiles = _environment.GetSpecialPath(SpecialPath.ProgramFilesX86);
    var root = programFiles.Combine(string.Concat("Microsoft Visual Studio ", version, "/Common7/IDE"));
    return root.CombineWithFilePath("mstest.exe");
}

This code assumes a specific path format, but it seems the format has been changed for Visual Studio 2017 (Community).
Old: Microsoft Visual Studio 14.0\Common7\IDE
New: Microsoft Visual Studio\2017\Community\Common7\IDE

I might send a pull request, as soon as I have time and I have the source code building :P

Great catch! Don't know why I didn't consider this when adding the MSBuild support for 2017. Temporarily you should be able to set the toolpath in the settings file. Let me know if you would like some assistance on the pull request, more than happy to help.

I meant you can set the ToolPath in the MSTestSettings class that you pass.

@dukeofharen to be clear, using this: Microsoft Visual Studio\2017\Community\Common7\IDE directly, isn't going to work. That path looks specific to the Community Edition of Visual Studio, and likely be different in the higher SKU's. As a result, any PR to correct this would need to delve a little deeper into finding the new location.

I've found this article about someone having problems locating the IDE folder: http://www.visualstudioextensibility.com/2016/11/23/some-implications-of-the-new-modular-setup-of-visual-studio-2017-for-vsx-developers/

You can install multiple versions of Visual Studio 2017 next to eachother. As far as I can tell, you only have the Community, Professional and Enterprise editions. Would it be OK to just check the existence of any of these 3 folders?

User can install in any drive, multiple versions is possible - especially if you have the build tools installed. But we could of course check the possible default paths first.

@phillipsj couldn't these paths also derive from the work done in #1520?

@devlead I was going to ask the same question, i.e. if the vswhere.exe could help.

@devlead @gep13 I think what we should do is to make defaults like we did in the MSBuild.
With that said I would want to refactor that all to make a VS2017ToolResolver that both tools could use to locate default Vs installs.

@dukeofharen there is also BuildTools location so that would need to be added too.

Let me know how you all want to proceed. Execution of this shouldn't be too difficult.

On Mar 8, 2017 4:40 AM, "Gary Ewan Park" notifications@github.com wrote:

@devlead https://github.com/devlead I was going to ask the same
question, i.e. if the vswhere.exe could help.

—
You are receiving this because you were mentioned.
Reply to this email directly, view it on GitHub
https://github.com/cake-build/cake/issues/1522#issuecomment-284994101,
or mute the thread
https://github.com/notifications/unsubscribe-auth/ABfthaf6lHE1MWBO9Oi671qzq86Z0RDzks5rjnelgaJpZM4MWI56
.

I had the same issue - as @phillipsj already mentioned, the ToolPath did the trick (even it is not super "clean")

MSTest(pathPattern, new MSTestSettings() { ....
                                 ToolPath = @"C:\Program Files (x86)\Microsoft Visual Studio\2017\Professional\Common7\IDE\MSTest.exe" });

I think similar problem is for VSTest
https://github.com/cake-build/cake/blob/develop/src/Cake.Common/Tools/VSTest/VSTestRunner.cs (at the bottom)
The default path (for professional) should be: C:\Program Files (x86)\Microsoft Visual Studio\2017\Professional\Common7\IDE\CommonExtensions\Microsoft\TestWindow\vstest.console.exe

Any chance this is going to be fixed soon?

@epot I've now marked issue up for grabs.
If someone want to take a stab at creating a PR let us know on this issue.

Ok, thanks :)

@devlead @gep13 I am getting back into the swing of things and if this is still an issue, I will take it.

@phillipsj If you didn't start on it yet I would like to allocate some time tomorrow to add MSTest 2017 support and prepare a pull request.

@bertvansteen nope, not yet. Take it if you want it.

Looking forward to the fix. This is the workaround I've been using:

// https://github.com/cake-build/cake/issues/1522
VSTestSettings FixToolPath(VSTestSettings settings)
{
    #tool vswhere
    settings.ToolPath =
        VSWhereLatest(new VSWhereLatestSettings { Requires = "Microsoft.VisualStudio.PackageGroup.TestTools.Core" })
        .CombineWithFilePath(File(@"Common7\IDE\CommonExtensions\Microsoft\TestWindow\vstest.console.exe"));
    return settings;
}

Then just wrap your settings:

VSTest("**/*.Tests.dll", FixToolPath(new VSTestSettings { Foo = 42 }))

(See https://github.com/Microsoft/vswhere/wiki/Find-VSTest.)

Maybe this was in the wrong place for VSTest, but I was redirected by https://github.com/cake-build/cake/issues/1763#issuecomment-323929748.

In 0.24.0, VSTest is still not being located by Cake and I'm still forced to use the workaround above.

I took a quick look at the changes here - the same funky pathing exists in VS 2019 as well. Given the pattern has been established already it looks like all that needs to be added for 2019 support is to include 2019/Professional, 2019/Community, and 2019/Enterprise in the search paths of MSTestRunner.cs line 117.

Was this page helpful?
0 / 5 - 0 ratings