ui: check validity of Python environment when entered in Python Source Group

* Python sourcegroup now displays if a provided Python environment is valid
* update used version of SourcetrailPythonIndexer
* changed executeProcess() to return the process' exit code and console output
This commit is contained in:
mlangkabel
2019-05-28 16:44:50 +02:00
parent b607933e0f
commit 31f4e47903
15 changed files with 92 additions and 31 deletions
+1 -1
View File
@@ -1,6 +1,6 @@
#!/bin/bash
SOURCETRAIL_PYTHON_INDEXER_VERSION="v0_db24_p1"
SOURCETRAIL_PYTHON_INDEXER_VERSION="v1_db24_p0"
# Determine current platform
PLATFORM='unknown'
+8 -2
View File
@@ -25,6 +25,7 @@ QtLocationPicker::QtLocationPicker(QWidget *parent)
m_data = new QtLineEdit(this);
m_data->setAttribute(Qt::WA_MacShowFocusRect, 0);
m_data->setObjectName("locationField");
connect(m_data, &QtLineEdit::textChanged, this, &QtLocationPicker::onDataTextChanged);
layout->addWidget(m_data);
m_button = new QtIconButton(
@@ -34,7 +35,7 @@ QtLocationPicker::QtLocationPicker(QWidget *parent)
m_button->setIconSize(QSize(16, 16));
m_button->setObjectName("dotsButton");
m_button->setToolTip("pick file");
connect(m_button, &QPushButton::clicked, this, &QtLocationPicker::handleButtonPress);
connect(m_button, &QPushButton::clicked, this, &QtLocationPicker::onHandleButtonPressed);
layout->addWidget(m_button);
setLayout(layout);
@@ -98,7 +99,7 @@ void QtLocationPicker::changeEvent(QEvent *event)
}
}
void QtLocationPicker::handleButtonPress()
void QtLocationPicker::onHandleButtonPressed()
{
FilePath path(m_data->text().toStdWString());
if (!path.empty() && !path.isAbsolute() && !m_relativeRootDirectory.empty())
@@ -124,3 +125,8 @@ void QtLocationPicker::handleButtonPress()
emit locationPicked();
}
}
void QtLocationPicker::onDataTextChanged(const QString& text)
{
emit textChanged(text);
}
+4 -3
View File
@@ -30,14 +30,15 @@ public:
signals:
void locationPicked();
void textChanged(const QString& text);
protected:
void changeEvent(QEvent *event) override;
private slots:
void handleButtonPress();
private:
void onHandleButtonPressed();
void onDataTextChanged(const QString& text);
QPushButton* m_button;
QtLineEdit* m_data;
@@ -6,16 +6,22 @@
#include <QMessageBox>
#include <QVBoxLayout>
#include "Application.h"
#include "ApplicationSettings.h"
#include "FileManager.h"
#include "MessageStatus.h"
#include "QtLocationPicker.h"
#include "QtDialogView.h"
#include "QtProjectWizzardContentPaths.h"
#include "ResourcePaths.h"
#include "ScopedFunctor.h"
#include "SonargraphProject.h"
#include "SourceGroupCxxCdb.h"
#include "SourceGroupCxxCodeblocks.h"
#include "SourceGroupCxxSonargraph.h"
#include "SourceGroupJavaSonargraph.h"
#include "SourceGroupJavaGradle.h"
#include "SourceGroupJavaMaven.h"
#include "QtLocationPicker.h"
#include "QtDialogView.h"
#include "QtProjectWizzardContentPaths.h"
#include "ApplicationSettings.h"
#include "SourceGroupSettingsCxxCdb.h"
#include "SourceGroupSettingsCxxCodeblocks.h"
#include "SourceGroupSettingsCxxSonargraph.h"
@@ -24,15 +30,11 @@
#include "SourceGroupSettingsJavaSonargraph.h"
#include "SourceGroupSettingsPythonEmpty.h"
#include "SourceGroupSettingsWithSonargraphProjectPath.h"
#include "FileManager.h"
#include "MessageStatus.h"
#include "SonargraphProject.h"
#include "ScopedFunctor.h"
#include "utility.h"
#include "utilityApp.h"
#include "utilityFile.h"
#include "utilityGradle.h"
#include "utilityMaven.h"
#include "Application.h"
QtProjectWizzardContentPath::QtProjectWizzardContentPath(QtProjectWizzardWindow* window)
: QtProjectWizzardContent(window)
@@ -744,6 +746,20 @@ QtProjectWizzardContentPathPythonEnvironment::QtProjectWizzardContentPathPythonE
setAllowEmpty(true);
}
void QtProjectWizzardContentPathPythonEnvironment::populate(QGridLayout* layout, int& row)
{
QtProjectWizzardContentPath::populate(layout, row);
connect(
m_picker, &QtLocationPicker::textChanged,
this, &QtProjectWizzardContentPathPythonEnvironment::onTextChanged
);
m_resultLabel = new QLabel();
m_resultLabel->setWordWrap(true);
layout->addWidget(m_resultLabel, row, QtProjectWizzardWindow::BACK_COL);
row++;
}
void QtProjectWizzardContentPathPythonEnvironment::load()
{
m_picker->setText(QString::fromStdWString(m_settings->getEnvironmentDirectoryPath().wstr()));
@@ -754,6 +770,39 @@ void QtProjectWizzardContentPathPythonEnvironment::save()
m_settings->setEnvironmentDirectoryPath(FilePath(m_picker->getText().toStdWString()));
}
void QtProjectWizzardContentPathPythonEnvironment::onTextChanged(const QString& text)
{
if (text.isEmpty())
{
m_resultLabel->clear();
}
else
{
m_resultLabel->setText("Checking validity of Python environment...");
std::thread([=]() {
std::pair<int, std::string> out = utility::executeProcess(
"\"" + ResourcePaths::getPythonPath().str() + "SourcetrailPythonIndexer\" check-environment " +
"--environment-path \"" + m_settings->makePathExpandedAndAbsolute(FilePath(text.toStdWString())).str() + "\"",
FilePath(),
5000
);
m_onQtThread(
[=]()
{
if (out.first == 0)
{
m_resultLabel->setText(QString::fromStdString(out.second));
}
else
{
m_resultLabel->setText("An error occurred while checking environment path. Unable to check validity.");
}
}
);
}).detach();
}
}
std::shared_ptr<SourceGroupSettings> QtProjectWizzardContentPathPythonEnvironment::getSourceGroupSettings()
{
return m_settings;
@@ -4,6 +4,7 @@
#include <set>
#include "QtProjectWizzardContent.h"
#include "QtThreadedFunctor.h"
#include "SingleValueCache.h"
class QCheckBox;
@@ -245,13 +246,17 @@ public:
QtProjectWizzardContentPathPythonEnvironment(std::shared_ptr<SourceGroupSettingsPythonEmpty> settings, QtProjectWizzardWindow* window);
// QtProjectWizzardContent implementation
void populate(QGridLayout* layout, int& row) override;
void load() override;
void save() override;
private:
void onTextChanged(const QString& text);
std::shared_ptr<SourceGroupSettings> getSourceGroupSettings() override;
std::shared_ptr<SourceGroupSettingsPythonEmpty> m_settings;
QtThreadedLambdaFunctor m_onQtThread;
QLabel* m_resultLabel;
};
#endif // QT_PROJECT_WIZZARD_CONTENT_PATH_H
@@ -26,7 +26,7 @@ void QtProjectWizzardContentSelect::populate(QGridLayout* layout, int& row)
{
std::string pythonIndexerVersion = " ";
{
std::string str = utility::executeProcess("\"" + ResourcePaths::getPythonPath().str() + "SourcetrailPythonIndexer\" --version", FilePath(), 5000);
std::string str = utility::executeProcess("\"" + ResourcePaths::getPythonPath().str() + "SourcetrailPythonIndexer\" --version", FilePath(), 5000).second;
std::regex regex("v\\d*\\.db\\d*\\.p\\d*"); // "\\d" matches any digit; "\\." matches the "." character
std::smatch matches;
std::regex_search(str, matches, regex);
@@ -23,7 +23,7 @@ std::vector<FilePath> CxxVs15HeaderPathDetector::getPaths() const
{
const std::string command = "\"" + expandedPaths[0].str() + "\" -latest -property installationPath";
const std::string command2 = "\"C:/Program Files (x86)/Microsoft Visual Studio/Installer/vswhere.exe\"";
const std::string output = utility::executeProcess(command, FilePath(), 10000);
const std::string output = utility::executeProcess(command, FilePath(), 10000).second;
const FilePath vsInstallPath(output);
if (vsInstallPath.exists())
@@ -12,7 +12,7 @@ namespace utility
std::vector<std::string> getCxxHeaderPaths(const std::string& compilerName)
{
std::string command = compilerName + " -x c++ -v -E /dev/null";
std::string clangOutput = utility::executeProcess(command.c_str());
std::string clangOutput = utility::executeProcess(command.c_str()).second;
std::string standardHeaders =
utility::substrBetween<std::string>(clangOutput, "#include <...> search starts here:\n","\nEnd of search list");
std::vector<std::string> paths;
@@ -19,7 +19,7 @@ JavaPathDetectorLinux::JavaPathDetectorLinux(const std::string javaVersion)
FilePath JavaPathDetectorLinux::getJavaInPath() const
{
std::string command = "which java";
std::string output = utility::executeProcess(command.c_str());
std::string output = utility::executeProcess(command.c_str()).second;
if (!output.empty())
{
@@ -38,7 +38,7 @@ FilePath JavaPathDetectorLinux::getJavaInPath() const
FilePath JavaPathDetectorLinux::readLink(const FilePath& path) const
{
std::string command = "readlink -f " + path.str();
FilePath javaPath( utility::executeProcess(command.c_str()));
FilePath javaPath( utility::executeProcess(command.c_str()).second);
if (!javaPath.empty())
{
return javaPath;
@@ -77,7 +77,7 @@ FilePath JavaPathDetectorLinux::getJavaInJavaHome() const
bool JavaPathDetectorLinux::checkVersion(const FilePath& path) const
{
std::string command = path.str() + " -version";
std::string output = utility::executeProcess(command.c_str());
std::string output = utility::executeProcess(command.c_str()).second;
return output.find(m_javaVersion) != std::string::npos;
}
@@ -15,7 +15,7 @@ std::vector<FilePath> JavaPathDetectorMac::getPaths() const
FilePath javaPath;
std::string command = "/usr/libexec/java_home";
std::string output = utility::executeProcess(command.c_str());
std::string output = utility::executeProcess(command.c_str()).second;
if (!output.empty())
{
@@ -11,7 +11,7 @@ MavenPathDetectorUnix::MavenPathDetectorUnix()
std::vector<FilePath> MavenPathDetectorUnix::getPaths() const
{
std::string command = "which mvn";
FilePath mavenPath(utility::executeProcess(command.c_str()));
FilePath mavenPath(utility::executeProcess(command.c_str()).second);
std::vector<FilePath> paths;
if (mavenPath.exists())
@@ -11,7 +11,7 @@ MavenPathDetectorWindows::MavenPathDetectorWindows()
std::vector<FilePath> MavenPathDetectorWindows::getPaths() const
{
std::string command = "cmd /c where mvn.cmd && exit";
FilePath mavenPath(utility::executeProcess(command.c_str()));
FilePath mavenPath(utility::executeProcess(command.c_str()).second);
std::vector<FilePath> paths;
if (mavenPath.exists())
+4 -4
View File
@@ -52,7 +52,7 @@ namespace utility
std::set<QProcess*> s_runningProcesses;
}
std::string utility::executeProcess(const std::string& command, const FilePath& workingDirectory, const int timeout)
std::pair<int, std::string> utility::executeProcess(const std::string& command, const FilePath& workingDirectory, const int timeout)
{
QProcess process;
process.setProcessChannelMode(QProcess::MergedChannels);
@@ -81,11 +81,11 @@ std::string utility::executeProcess(const std::string& command, const FilePath&
// QProcess::ProcessError error = process.error();
std::string processoutput = process.readAll().toStdString();
const std::string processoutput = process.readAll().toStdString();
const int exitCode = process.exitCode();
process.close();
processoutput = utility::trim(processoutput);
return processoutput;
return std::make_pair(exitCode, utility::trim(processoutput));
}
std::string utility::executeProcessUntilNoOutput(const std::string& command, const FilePath& workingDirectory, const int waitTime)
+1 -1
View File
@@ -12,7 +12,7 @@ class License;
namespace utility
{
std::string executeProcess(const std::string& command, const FilePath& workingDirectory = FilePath(), const int timeout = 30000);
std::pair<int, std::string> executeProcess(const std::string& command, const FilePath& workingDirectory = FilePath(), const int timeout = 30000);
std::string executeProcessUntilNoOutput(const std::string& command, const FilePath& workingDirectory, int waitTime = 10000);
int executeProcessAndGetExitCode(
const std::wstring& commandPath,
@@ -49,7 +49,7 @@ std::vector<std::shared_ptr<IndexerCommand>> SourceGroupPythonEmpty::getIndexerC
if (!m_settings->getEnvironmentDirectoryPath().empty())
{
args += L" --environment-directory-path=" + m_settings->getEnvironmentDirectoryPathExpandedAndAbsolute().wstr();
args += L" --environment-path=" + m_settings->getEnvironmentDirectoryPathExpandedAndAbsolute().wstr();
}
if (ApplicationSettings::getInstance()->getVerboseIndexerLoggingEnabled())
@@ -64,7 +64,7 @@ std::vector<std::shared_ptr<IndexerCommand>> SourceGroupPythonEmpty::getIndexerC
{
indexerCommands.push_back(std::make_shared<IndexerCommandCustom>(
INDEXER_COMMAND_PYTHON,
L"\"" + ResourcePaths::getPythonPath().wstr() + L"SourcetrailPythonIndexer\"" + args,
L"\"" + ResourcePaths::getPythonPath().wstr() + L"SourcetrailPythonIndexer\" index" + args,
m_settings->getProjectSettings()->getProjectFilePath(),
m_settings->getProjectSettings()->getTempDBFilePath(),
std::to_wstring(SqliteIndexStorage::getStorageVersion()),