forked from qt-creator/qt-creator
VcsCommand: Don't derive from ShellCommand
Transform VcsCommand into VcsCommandDecorator and attach it to ShellCommand. There is no need to derive from ShellCommand anymore. Use ShellCommand's public API to setup vcs command via VcsCommandDecorator. Make ShellCommand final. Change-Id: I39e3699c80a9e108bcaeef7fb02214e2cc0d0dee Reviewed-by: Orgad Shaneh <orgads@gmail.com>
This commit is contained in:
@@ -162,6 +162,11 @@ const FilePath &ShellCommand::defaultWorkingDirectory() const
|
|||||||
return d->m_defaultWorkingDirectory;
|
return d->m_defaultWorkingDirectory;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Environment ShellCommand::environment() const
|
||||||
|
{
|
||||||
|
return d->m_environment;
|
||||||
|
}
|
||||||
|
|
||||||
void ShellCommand::setEnvironment(const Environment &env)
|
void ShellCommand::setEnvironment(const Environment &env)
|
||||||
{
|
{
|
||||||
d->m_environment = env;
|
d->m_environment = env;
|
||||||
|
@@ -68,7 +68,7 @@ private:
|
|||||||
friend class ShellCommand;
|
friend class ShellCommand;
|
||||||
};
|
};
|
||||||
|
|
||||||
class QTCREATOR_UTILS_EXPORT ShellCommand : public QObject
|
class QTCREATOR_UTILS_EXPORT ShellCommand final : public QObject
|
||||||
{
|
{
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
@@ -98,6 +98,11 @@ public:
|
|||||||
QString displayName() const;
|
QString displayName() const;
|
||||||
void setDisplayName(const QString &name);
|
void setDisplayName(const QString &name);
|
||||||
|
|
||||||
|
const FilePath &defaultWorkingDirectory() const;
|
||||||
|
|
||||||
|
Environment environment() const;
|
||||||
|
void setEnvironment(const Environment &env);
|
||||||
|
|
||||||
void addJob(const CommandLine &command,
|
void addJob(const CommandLine &command,
|
||||||
const FilePath &workingDirectory = {},
|
const FilePath &workingDirectory = {},
|
||||||
const ExitCodeInterpreter &interpreter = {});
|
const ExitCodeInterpreter &interpreter = {});
|
||||||
@@ -107,8 +112,6 @@ public:
|
|||||||
void execute(); // Execute tasks asynchronously!
|
void execute(); // Execute tasks asynchronously!
|
||||||
void abort();
|
void abort();
|
||||||
|
|
||||||
const FilePath &defaultWorkingDirectory() const;
|
|
||||||
|
|
||||||
int defaultTimeoutS() const;
|
int defaultTimeoutS() const;
|
||||||
void setDefaultTimeoutS(int timeout);
|
void setDefaultTimeoutS(int timeout);
|
||||||
|
|
||||||
@@ -133,6 +136,9 @@ public:
|
|||||||
|
|
||||||
void cancel();
|
void cancel();
|
||||||
|
|
||||||
|
void setDisableUnixTerminal();
|
||||||
|
int timeoutS() const;
|
||||||
|
|
||||||
signals:
|
signals:
|
||||||
void stdOutText(const QString &);
|
void stdOutText(const QString &);
|
||||||
void stdErrText(const QString &);
|
void stdErrText(const QString &);
|
||||||
@@ -151,11 +157,6 @@ signals:
|
|||||||
void executedAsync(const QFuture<void> &future);
|
void executedAsync(const QFuture<void> &future);
|
||||||
void runCommandFinished(const Utils::FilePath &workingDirectory);
|
void runCommandFinished(const Utils::FilePath &workingDirectory);
|
||||||
|
|
||||||
protected:
|
|
||||||
void setEnvironment(const Environment &env);
|
|
||||||
void setDisableUnixTerminal();
|
|
||||||
int timeoutS() const;
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
FilePath workDirectory(const FilePath &wd) const;
|
FilePath workDirectory(const FilePath &wd) const;
|
||||||
void run(QFutureInterface<void> &future);
|
void run(QFutureInterface<void> &future);
|
||||||
|
@@ -77,62 +77,60 @@ static IEditor *locateEditor(const char *property, const QString &entry)
|
|||||||
|
|
||||||
namespace VcsBase {
|
namespace VcsBase {
|
||||||
|
|
||||||
class VcsCommand : public ShellCommand
|
class VcsCommandDecorator : public QObject
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
VcsCommand(const FilePath &defaultWorkingDirectory, const Environment &environment);
|
VcsCommandDecorator(ShellCommand *command);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void addTask(const QFuture<void> &future);
|
void addTask(const QFuture<void> &future);
|
||||||
void postRunCommand(const Utils::FilePath &workDirectory);
|
void postRunCommand(const FilePath &workingDirectory);
|
||||||
|
|
||||||
|
ShellCommand *m_command;
|
||||||
};
|
};
|
||||||
|
|
||||||
VcsCommand::VcsCommand(const FilePath &workingDirectory, const Environment &environment)
|
VcsCommandDecorator::VcsCommandDecorator(ShellCommand *command)
|
||||||
: ShellCommand(workingDirectory, environment)
|
: QObject(command)
|
||||||
|
, m_command(command)
|
||||||
{
|
{
|
||||||
Environment env = environment;
|
Environment env = m_command->environment();
|
||||||
VcsBase::setProcessEnvironment(&env);
|
VcsBase::setProcessEnvironment(&env);
|
||||||
setEnvironment(env);
|
m_command->setEnvironment(env);
|
||||||
|
|
||||||
VcsOutputWindow::setRepository(workingDirectory.toString());
|
VcsOutputWindow::setRepository(m_command->defaultWorkingDirectory().toString());
|
||||||
setDisableUnixTerminal();
|
m_command->setDisableUnixTerminal();
|
||||||
|
connect(m_command, &ShellCommand::started, this, [this] {
|
||||||
connect(this, &ShellCommand::started, this, [this] {
|
if (m_command->flags() & ShellCommand::ExpectRepoChanges)
|
||||||
if (flags() & ExpectRepoChanges)
|
|
||||||
GlobalFileChangeBlocker::instance()->forceBlocked(true);
|
GlobalFileChangeBlocker::instance()->forceBlocked(true);
|
||||||
});
|
});
|
||||||
connect(this, &ShellCommand::finished, this, [this] {
|
connect(m_command, &ShellCommand::finished, this, [this] {
|
||||||
if (flags() & ExpectRepoChanges)
|
if (m_command->flags() & ShellCommand::ExpectRepoChanges)
|
||||||
GlobalFileChangeBlocker::instance()->forceBlocked(false);
|
GlobalFileChangeBlocker::instance()->forceBlocked(false);
|
||||||
});
|
});
|
||||||
|
|
||||||
VcsOutputWindow *outputWindow = VcsOutputWindow::instance();
|
VcsOutputWindow *outputWindow = VcsOutputWindow::instance();
|
||||||
connect(this, &ShellCommand::append, outputWindow, [outputWindow](const QString &t) {
|
connect(m_command, &ShellCommand::append, outputWindow, [outputWindow](const QString &t) {
|
||||||
outputWindow->append(t);
|
outputWindow->append(t);
|
||||||
});
|
});
|
||||||
connect(this, &ShellCommand::appendSilently, outputWindow, &VcsOutputWindow::appendSilently);
|
connect(m_command, &ShellCommand::appendSilently, outputWindow, &VcsOutputWindow::appendSilently);
|
||||||
connect(this, &ShellCommand::appendError, outputWindow, &VcsOutputWindow::appendError);
|
connect(m_command, &ShellCommand::appendError, outputWindow, &VcsOutputWindow::appendError);
|
||||||
connect(this, &ShellCommand::appendCommand, outputWindow, &VcsOutputWindow::appendCommand);
|
connect(m_command, &ShellCommand::appendCommand, outputWindow, &VcsOutputWindow::appendCommand);
|
||||||
connect(this, &ShellCommand::appendMessage, outputWindow, &VcsOutputWindow::appendMessage);
|
connect(m_command, &ShellCommand::appendMessage, outputWindow, &VcsOutputWindow::appendMessage);
|
||||||
|
connect(m_command, &ShellCommand::executedAsync, this, &VcsCommandDecorator::addTask);
|
||||||
connect(this, &ShellCommand::executedAsync, this, &VcsCommand::addTask);
|
const auto connection = connect(m_command, &ShellCommand::runCommandFinished,
|
||||||
const auto connection = connect(this, &ShellCommand::runCommandFinished,
|
this, &VcsCommandDecorator::postRunCommand);
|
||||||
this, &VcsCommand::postRunCommand);
|
connect(ICore::instance(), &ICore::coreAboutToClose, this, [connection] {
|
||||||
|
|
||||||
connect(ICore::instance(), &ICore::coreAboutToClose, this, [this, connection] {
|
|
||||||
disconnect(connection);
|
disconnect(connection);
|
||||||
abort();
|
abort();
|
||||||
});
|
});}
|
||||||
}
|
|
||||||
|
|
||||||
void VcsCommand::addTask(const QFuture<void> &future)
|
void VcsCommandDecorator::addTask(const QFuture<void> &future)
|
||||||
{
|
{
|
||||||
if ((flags() & SuppressCommandLogging))
|
if ((m_command->flags() & ShellCommand::SuppressCommandLogging))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
const QString name = displayName();
|
const QString name = m_command->displayName();
|
||||||
const auto id = Id::fromString(name + QLatin1String(".action"));
|
const auto id = Id::fromString(name + QLatin1String(".action"));
|
||||||
if (hasProgressParser()) {
|
if (m_command->hasProgressParser()) {
|
||||||
ProgressManager::addTask(future, name, id);
|
ProgressManager::addTask(future, name, id);
|
||||||
} else {
|
} else {
|
||||||
// add a timed tasked based on timeout
|
// add a timed tasked based on timeout
|
||||||
@@ -146,22 +144,21 @@ void VcsCommand::addTask(const QFuture<void> &future)
|
|||||||
watcher->deleteLater();
|
watcher->deleteLater();
|
||||||
});
|
});
|
||||||
watcher->setFuture(future);
|
watcher->setFuture(future);
|
||||||
ProgressManager::addTimedTask(*fi, name, id, qMax(2, timeoutS() / 5)/*itsmagic*/);
|
ProgressManager::addTimedTask(*fi, name, id, qMax(2, m_command->timeoutS() / 5));
|
||||||
}
|
}
|
||||||
|
|
||||||
Internal::VcsPlugin::addFuture(future);
|
Internal::VcsPlugin::addFuture(future);
|
||||||
}
|
}
|
||||||
|
|
||||||
void VcsCommand::postRunCommand(const FilePath &workingDirectory)
|
void VcsCommandDecorator::postRunCommand(const FilePath &workingDirectory)
|
||||||
{
|
{
|
||||||
if (!(flags() & ShellCommand::ExpectRepoChanges))
|
if (!(m_command->flags() & ShellCommand::ExpectRepoChanges))
|
||||||
return;
|
return;
|
||||||
// TODO tell the document manager that the directory now received all expected changes
|
// TODO tell the document manager that the directory now received all expected changes
|
||||||
// Core::DocumentManager::unexpectDirectoryChange(d->m_workingDirectory);
|
// Core::DocumentManager::unexpectDirectoryChange(d->m_workingDirectory);
|
||||||
VcsManager::emitRepositoryChanged(workingDirectory);
|
VcsManager::emitRepositoryChanged(workingDirectory);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
VcsBaseClientImpl::VcsBaseClientImpl(VcsBaseSettings *baseSettings)
|
VcsBaseClientImpl::VcsBaseClientImpl(VcsBaseSettings *baseSettings)
|
||||||
: m_baseSettings(baseSettings)
|
: m_baseSettings(baseSettings)
|
||||||
{
|
{
|
||||||
@@ -257,7 +254,8 @@ void VcsBaseClientImpl::vcsFullySynchronousExec(QtcProcess &proc,
|
|||||||
const FilePath &workingDir, const CommandLine &cmdLine,
|
const FilePath &workingDir, const CommandLine &cmdLine,
|
||||||
unsigned flags, int timeoutS, QTextCodec *codec) const
|
unsigned flags, int timeoutS, QTextCodec *codec) const
|
||||||
{
|
{
|
||||||
VcsCommand command(workingDir, processEnvironment());
|
ShellCommand command(workingDir, processEnvironment());
|
||||||
|
new VcsCommandDecorator(&command);
|
||||||
command.addFlags(flags);
|
command.addFlags(flags);
|
||||||
if (codec)
|
if (codec)
|
||||||
command.setCodec(codec);
|
command.setCodec(codec);
|
||||||
@@ -305,7 +303,8 @@ void VcsBaseClientImpl::vcsSynchronousExec(QtcProcess &proc,
|
|||||||
QTextCodec *outputCodec) const
|
QTextCodec *outputCodec) const
|
||||||
{
|
{
|
||||||
Environment env = processEnvironment();
|
Environment env = processEnvironment();
|
||||||
VcsCommand command(workingDir, env.isValid() ? env : Environment::systemEnvironment());
|
ShellCommand command(workingDir, env.isValid() ? env : Environment::systemEnvironment());
|
||||||
|
new VcsCommandDecorator(&command);
|
||||||
proc.setTimeoutS(vcsTimeoutS());
|
proc.setTimeoutS(vcsTimeoutS());
|
||||||
command.addFlags(flags);
|
command.addFlags(flags);
|
||||||
command.setCodec(outputCodec);
|
command.setCodec(outputCodec);
|
||||||
@@ -320,7 +319,9 @@ int VcsBaseClientImpl::vcsTimeoutS() const
|
|||||||
ShellCommand *VcsBaseClientImpl::createVcsCommand(const FilePath &defaultWorkingDir,
|
ShellCommand *VcsBaseClientImpl::createVcsCommand(const FilePath &defaultWorkingDir,
|
||||||
const Environment &environment)
|
const Environment &environment)
|
||||||
{
|
{
|
||||||
return new VcsCommand(defaultWorkingDir, environment);
|
ShellCommand *command = new ShellCommand(defaultWorkingDir, environment);
|
||||||
|
new VcsCommandDecorator(command);
|
||||||
|
return command;
|
||||||
}
|
}
|
||||||
|
|
||||||
VcsBaseEditorWidget *VcsBaseClientImpl::createVcsEditor(Id kind, QString title,
|
VcsBaseEditorWidget *VcsBaseClientImpl::createVcsEditor(Id kind, QString title,
|
||||||
|
Reference in New Issue
Block a user