AutoTest: Allow basic filtering of scanned folders

This allows to specify folders to be used as search folders
while scanning for tests.
Current approach allows simple folder names or folder structures
without wildcards.

Examples:
Value                What will be (recursively) scanned
tests                if the current project has any (not necessarily
                     a direct) subfolder 'tests' this folder will be
                     scanned
tests/auto           if the current project has any (not necessarily
                     a direct) subfolder 'tests' and this folder has
                     a direct subfolder 'auto' the 'auto' folder will
                     be scanned
If there are more folders which apply to the rules then all of them
will be scanned.
This filtering will not keep the parser inside these folders as it
might be necessary to step into different folders because of
dependencies if the found tests, but the search for entry points to
tests will be limited to these folders.

Task-number: QTCREATORBUG-16705
Change-Id: Ib93465540cd20656d033e16205807aba6830d738
Reviewed-by: Leena Miettinen <riitta-leena.miettinen@qt.io>
Reviewed-by: David Schulz <david.schulz@qt.io>
This commit is contained in:
Christian Stenger
2017-01-06 07:20:25 +01:00
parent 34504ad797
commit 67aea18cc2
6 changed files with 316 additions and 4 deletions

View File

@@ -25,10 +25,13 @@
#include "autotestconstants.h"
#include "autotest_utils.h"
#include "autotestplugin.h"
#include "testcodeparser.h"
#include "testframeworkmanager.h"
#include "testsettings.h"
#include <coreplugin/editormanager/editormanager.h>
#include <coreplugin/messagemanager.h>
#include <coreplugin/progressmanager/futureprogress.h>
#include <coreplugin/progressmanager/progressmanager.h>
#include <cpptools/cpptoolsconstants.h>
@@ -160,6 +163,28 @@ void TestCodeParser::updateTestTree()
scanForTests();
}
static QStringList filterFiles(const QString &projectDir, const QStringList &files)
{
const QSharedPointer<TestSettings> &settings = AutotestPlugin::instance()->settings();
const QSet<QString> &filters = settings->whiteListFilters.toSet(); // avoid duplicates
if (!settings->filterScan || filters.isEmpty())
return files;
QStringList finalResult;
for (const QString &file : files) {
// apply filter only below project directory if file is part of a project
const QString &fileToProcess = file.startsWith(projectDir)
? file.mid(projectDir.size())
: file;
for (const QString &filter : filters) {
if (fileToProcess.contains(filter)) {
finalResult.push_back(file);
break;
}
}
}
return finalResult;
}
// used internally to indicate a parse that failed due to having triggered a parse for a file that
// is not (yet) part of the CppModelManager's snapshot
static bool parsingHasFailed;
@@ -302,9 +327,12 @@ void TestCodeParser::scanForTests(const QStringList &fileList)
m_reparseTimerTimedOut = false;
m_postponedFiles.clear();
bool isFullParse = fileList.isEmpty();
ProjectExplorer::Project *project = ProjectExplorer::SessionManager::startupProject();
if (!project)
return;
QStringList list;
if (isFullParse) {
list = ProjectExplorer::SessionManager::startupProject()->files(ProjectExplorer::Project::SourceFiles);
list = project->files(ProjectExplorer::Project::SourceFiles);
if (list.isEmpty()) {
// at least project file should be there, but might happen if parsing current project
// takes too long, especially when opening sessions holding multiple projects
@@ -333,6 +361,17 @@ void TestCodeParser::scanForTests(const QStringList &fileList)
m_model->markForRemoval(filePath);
}
list = filterFiles(project->projectDirectory().toString(), list);
if (list.isEmpty()) {
if (isFullParse) {
Core::MessageManager::instance()->write(
tr("AutoTest Plugin WARNING: No files left after filtering test scan "
"folders. Check test filter settings."),
Core::MessageManager::Flash);
}
onFinished();
return;
}
qCDebug(LOG) << QDateTime::currentDateTime().toString("hh:mm:ss.zzz") << "StartParsing";
foreach (ITestParser *parser, m_testCodeParsers)
parser->init(list);