Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Support wildcard in filenames #2096

Merged
merged 11 commits into from Aug 8, 2019
39 changes: 7 additions & 32 deletions src/vstest.console/CommandLine/CommandLineOptions.cs
Expand Up @@ -5,7 +5,6 @@ namespace Microsoft.VisualStudio.TestPlatform.CommandLine
{
using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;

using Microsoft.VisualStudio.TestPlatform.ObjectModel;
Expand Down Expand Up @@ -84,6 +83,7 @@ protected CommandLineOptions()
this.BatchSize = DefaultBatchSize;
this.TestStatsEventTimeout = this.DefaultRetrievalTimeout;
this.FileHelper = new FileHelper();
vagisha-nidhi marked this conversation as resolved.
Show resolved Hide resolved
this.FilePatternParser = new FilePatternParser();
#if TODO
UseVsixExtensions = Utilities.GetAppSettingValue(UseVsixExtensionsKey, false);
#endif
Expand Down Expand Up @@ -239,6 +239,8 @@ public bool ShouldCollectSourceInformation

internal IFileHelper FileHelper { get; set; }

internal FilePatternParser FilePatternParser { get; set; }

/// <summary>
/// Gets or sets the target Framework version for test run.
/// </summary>
Expand Down Expand Up @@ -293,38 +295,11 @@ public void AddSource(string source)
source = Path.Combine(FileHelper.GetCurrentDirectory(), source);
}

var filePatternParser = new FilePatternParser();
var sourceFiles = new List<string>();
var isValidPattern = filePatternParser.IsValidPattern(source, out sourceFiles);

// If the given file is a valid pattern
if (isValidPattern)
{
foreach (var sourceFile in sourceFiles)
{
if (this.sources.Contains(sourceFile, StringComparer.OrdinalIgnoreCase))
{
continue;
}
// Get matching files from file pattern parser
var matchingFiles = FilePatternParser.GetMatchingFiles(source);

this.sources.Add(sourceFile);
}

return;
}

// If the given file is not a pattern, check if it exists.
if (!FileHelper.Exists(source))
{
throw new CommandLineException(
string.Format(CultureInfo.CurrentUICulture, CommandLineResources.TestSourceFileNotFound, source));
}

// Add the file to the source list if not already present.
if (!this.sources.Contains(source, StringComparer.OrdinalIgnoreCase))
{
this.sources.Add(source);
}
// Add the matching files to source list
this.sources = this.sources.Union(matchingFiles).ToList();
}

#endregion
Expand Down
34 changes: 26 additions & 8 deletions src/vstest.console/Internal/FilePatternParser.cs
Expand Up @@ -5,43 +5,61 @@ namespace vstest.console.Internal
{
using Microsoft.Extensions.FileSystemGlobbing;
using Microsoft.Extensions.FileSystemGlobbing.Abstractions;
using Microsoft.VisualStudio.TestPlatform.CommandLine;
using Microsoft.VisualStudio.TestPlatform.ObjectModel;
using Microsoft.VisualStudio.TestPlatform.Utilities.Helpers;
using Microsoft.VisualStudio.TestPlatform.Utilities.Helpers.Interfaces;
using System;
using System.Collections.Generic;
using System.Globalization;
using System.IO;

using CommandLineResources = Microsoft.VisualStudio.TestPlatform.CommandLine.Resources.Resources;

/// <summary>
/// Class for getting matching files from wild card pattern file name
/// Microsoft.Extensions.FileSystemGlobbing methods used to get matching file names
/// </summary>
public class FilePatternParser
{
private Matcher matcher;
private IFileHelper fileHelper;
private char[] wildCardCharacters = { '*' };

public FilePatternParser()
: this(new Matcher())
: this(new Matcher(), new FileHelper())
{
}

internal FilePatternParser(Matcher matcher)
internal FilePatternParser(Matcher matcher, IFileHelper fileHelper)
{
this.matcher = matcher;
this.fileHelper = fileHelper;
}

/// <summary>
/// Used to get matching files with pattern
/// </summary>
/// <returns>If the file is a valid pattern or full path. Returns true if it is valid pattern</returns>
public bool IsValidPattern(string filePattern, out List<string> matchingFiles)
/// <returns>Returns the list of matching files</returns>
public List<string> GetMatchingFiles(string filePattern)
{
vagisha-nidhi marked this conversation as resolved.
Show resolved Hide resolved
matchingFiles = new List<string>();
var matchingFiles = new List<string>();

// If there is no wildcard, return false.
// If there is no wildcard simply add the file to the list of matching files.
if(filePattern.IndexOfAny(wildCardCharacters) == -1)
{
EqtTrace.Info($"FilePatternParser: The given file {filePattern} is a full path.");
return false;

// Check if the file exists.
if (!this.fileHelper.Exists(filePattern))
{
throw new CommandLineException(
string.Format(CultureInfo.CurrentUICulture, CommandLineResources.TestSourceFileNotFound, filePattern));
}

matchingFiles.Add(filePattern);

return matchingFiles;
}

// Split the given wildcard into search directory and pattern to be searched.
Expand All @@ -59,7 +77,7 @@ public bool IsValidPattern(string filePattern, out List<string> matchingFiles)
matchingFiles.Add(Path.Combine(splitPattern.Item1, match.Path));
}

return true;
return matchingFiles;
}

/// <summary>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/Resources.resx
Expand Up @@ -484,7 +484,7 @@
<data name="RunTestsArgumentHelp" xml:space="preserve">
<value>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</value>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.cs.xlf
Expand Up @@ -291,7 +291,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.de.xlf
Expand Up @@ -291,7 +291,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.es.xlf
Expand Up @@ -291,7 +291,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.fr.xlf
Expand Up @@ -291,7 +291,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.it.xlf
Expand Up @@ -291,7 +291,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.ja.xlf
Expand Up @@ -291,7 +291,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.ko.xlf
Expand Up @@ -291,7 +291,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.pl.xlf
Expand Up @@ -291,7 +291,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.pt-BR.xlf
Expand Up @@ -291,7 +291,7 @@ Altere o prefixo de nível de diagnóstico do agente de console, como mostrado a
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.ru.xlf
Expand Up @@ -291,7 +291,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.tr.xlf
Expand Up @@ -291,7 +291,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.xlf
Expand Up @@ -121,7 +121,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.zh-Hans.xlf
Expand Up @@ -290,7 +290,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
2 changes: 1 addition & 1 deletion src/vstest.console/Resources/xlf/Resources.zh-Hant.xlf
Expand Up @@ -292,7 +292,7 @@
<trans-unit id="RunTestsArgumentHelp">
<source>[TestFileNames]
Run tests from the specified files or wild card pattern. Separate multiple test file names or pattern
by spaces. Use detailed verbosity to view matched test files.
by spaces. Set console logger verbosity to detailed to view matched test files.
Examples: mytestproject.dll
mytestproject.dll myothertestproject.exe
testproject*.dll my*project.dll</source>
Expand Down
Expand Up @@ -12,18 +12,23 @@ namespace Microsoft.VisualStudio.TestPlatform.CommandLine.UnitTests.CommandLine
using Moq;
using System.IO;
using MSTest.TestFramework.AssertExtensions;
using vstest.console.Internal;
using Microsoft.Extensions.FileSystemGlobbing;

[TestClass]
public class CommandLineOptionsTests
{
private readonly Mock<IFileHelper> fileHelper;
private FilePatternParser filePatternParser;
private readonly string currentDirectory = @"C:\\Temp";

public CommandLineOptionsTests()
{
this.fileHelper = new Mock<IFileHelper>();
this.filePatternParser = new FilePatternParser(new Mock<Matcher>().Object, this.fileHelper.Object);
CommandLineOptions.Instance.Reset();
CommandLineOptions.Instance.FileHelper = this.fileHelper.Object;
CommandLineOptions.Instance.FilePatternParser = this.filePatternParser;
this.fileHelper.Setup(fh => fh.GetCurrentDirectory()).Returns(currentDirectory);
}

Expand Down Expand Up @@ -90,28 +95,5 @@ public void CommandLineOptionsAddSourceShouldAddSourceForValidSource()

Assert.IsTrue(CommandLineOptions.Instance.Sources.Contains(testFilePath));
}

[TestMethod]
public void CommandLineOptionsShouldCheckIfFileExistesIfFilePathDoesNotContainPattern()
{
string testFilePath = "C:\\DummyTestFile.txt";
this.fileHelper.Setup(fh => fh.Exists(testFilePath)).Returns(true);

CommandLineOptions.Instance.AddSource(testFilePath);

this.fileHelper.Verify(x => x.Exists("C:\\DummyTestFile.txt"), Times.Once);
Assert.IsTrue(CommandLineOptions.Instance.Sources.Contains(testFilePath));
}

[TestMethod]
public void CommandLineOptionsShouldCheckIfFileExistesIfFilePathContainsPattern()
{
string testFilePath = "C:\\Folder1\\Folder*\\DummyTestFile.txt";
this.fileHelper.Setup(fh => fh.Exists(testFilePath)).Returns(true);

CommandLineOptions.Instance.AddSource(testFilePath);

this.fileHelper.Verify(x => x.Exists(It.IsAny<string>()), Times.Never);
}
}
}