Improve command line parameters dispatching

Encapsulate parameters dispatching in Application class.
Avoid serializing parameters when it is not necessary.

PR #18469.
This commit is contained in:
Vladimir Golovnev 2023-02-02 10:02:51 +03:00 committed by GitHub
parent 09e58df03f
commit 0dcbf9f698
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
5 changed files with 147 additions and 156 deletions

View file

@ -122,6 +122,104 @@ namespace
#ifndef DISABLE_GUI
const int PIXMAP_CACHE_SIZE = 64 * 1024 * 1024; // 64MiB
#endif
QString serializeParams(const QBtCommandLineParameters &params)
{
QStringList result;
// Because we're passing a string list to the currently running
// qBittorrent process, we need some way of passing along the options
// the user has specified. Here we place special strings that are
// almost certainly not going to collide with a file path or URL
// specified by the user, and placing them at the beginning of the
// string list so that they will be processed before the list of
// torrent paths or URLs.
const BitTorrent::AddTorrentParams &addTorrentParams = params.addTorrentParams;
if (!addTorrentParams.savePath.isEmpty())
result.append(u"@savePath=" + addTorrentParams.savePath.data());
if (addTorrentParams.addPaused.has_value())
result.append(*addTorrentParams.addPaused ? u"@addPaused=1"_qs : u"@addPaused=0"_qs);
if (addTorrentParams.skipChecking)
result.append(u"@skipChecking"_qs);
if (!addTorrentParams.category.isEmpty())
result.append(u"@category=" + addTorrentParams.category);
if (addTorrentParams.sequential)
result.append(u"@sequential"_qs);
if (addTorrentParams.firstLastPiecePriority)
result.append(u"@firstLastPiecePriority"_qs);
if (params.skipDialog.has_value())
result.append(*params.skipDialog ? u"@skipDialog=1"_qs : u"@skipDialog=0"_qs);
result += params.torrentSources;
return result.join(PARAMS_SEPARATOR);
}
QBtCommandLineParameters parseParams(const QString &str)
{
QBtCommandLineParameters parsedParams;
BitTorrent::AddTorrentParams &addTorrentParams = parsedParams.addTorrentParams;
for (QString param : asConst(str.split(PARAMS_SEPARATOR, Qt::SkipEmptyParts)))
{
param = param.trimmed();
// Process strings indicating options specified by the user.
if (param.startsWith(u"@savePath="))
{
addTorrentParams.savePath = Path(param.mid(10));
continue;
}
if (param.startsWith(u"@addPaused="))
{
addTorrentParams.addPaused = (QStringView(param).mid(11).toInt() != 0);
continue;
}
if (param == u"@skipChecking")
{
addTorrentParams.skipChecking = true;
continue;
}
if (param.startsWith(u"@category="))
{
addTorrentParams.category = param.mid(10);
continue;
}
if (param == u"@sequential")
{
addTorrentParams.sequential = true;
continue;
}
if (param == u"@firstLastPiecePriority")
{
addTorrentParams.firstLastPiecePriority = true;
continue;
}
if (param.startsWith(u"@skipDialog="))
{
parsedParams.skipDialog = (QStringView(param).mid(12).toInt() != 0);
continue;
}
parsedParams.torrentSources.append(param);
}
return parsedParams;
}
}
Application::Application(int &argc, char **argv)
@ -390,7 +488,7 @@ void Application::processMessage(const QString &message)
}
#endif
const AddTorrentParams params = parseParams(message.split(PARAMS_SEPARATOR, Qt::SkipEmptyParts));
const QBtCommandLineParameters params = parseParams(message);
// If Application is not allowed to process params immediately
// (i.e., other components are not ready) store params
if (m_isProcessingParamsAllowed)
@ -625,71 +723,12 @@ void Application::allTorrentsFinished()
exit();
}
bool Application::sendParams(const QStringList &params)
bool Application::callMainInstance()
{
return m_instanceManager->sendMessage(params.join(PARAMS_SEPARATOR));
return m_instanceManager->sendMessage(serializeParams(commandLineArgs()));
}
Application::AddTorrentParams Application::parseParams(const QStringList &params) const
{
AddTorrentParams parsedParams;
BitTorrent::AddTorrentParams &torrentParams = parsedParams.torrentParams;
for (QString param : params)
{
param = param.trimmed();
// Process strings indicating options specified by the user.
if (param.startsWith(u"@savePath="))
{
torrentParams.savePath = Path(param.mid(10));
continue;
}
if (param.startsWith(u"@addPaused="))
{
torrentParams.addPaused = (QStringView(param).mid(11).toInt() != 0);
continue;
}
if (param == u"@skipChecking")
{
torrentParams.skipChecking = true;
continue;
}
if (param.startsWith(u"@category="))
{
torrentParams.category = param.mid(10);
continue;
}
if (param == u"@sequential")
{
torrentParams.sequential = true;
continue;
}
if (param == u"@firstLastPiecePriority")
{
torrentParams.firstLastPiecePriority = true;
continue;
}
if (param.startsWith(u"@skipDialog="))
{
parsedParams.skipTorrentDialog = (QStringView(param).mid(12).toInt() != 0);
continue;
}
parsedParams.torrentSources.append(param);
}
return parsedParams;
}
void Application::processParams(const AddTorrentParams &params)
void Application::processParams(const QBtCommandLineParameters &params)
{
#ifndef DISABLE_GUI
// There are two circumstances in which we want to show the torrent
@ -697,21 +736,21 @@ void Application::processParams(const AddTorrentParams &params)
// be shown and skipTorrentDialog is undefined. The other is when
// skipTorrentDialog is false, meaning that the application setting
// should be overridden.
const bool showDialogForThisTorrent = !params.skipTorrentDialog.value_or(!AddNewTorrentDialog::isEnabled());
if (showDialogForThisTorrent)
const bool showDialog = !params.skipDialog.value_or(!AddNewTorrentDialog::isEnabled());
if (showDialog)
{
for (const QString &torrentSource : params.torrentSources)
AddNewTorrentDialog::show(torrentSource, params.torrentParams, m_window);
AddNewTorrentDialog::show(torrentSource, params.addTorrentParams, m_window);
}
else
#endif
{
for (const QString &torrentSource : params.torrentSources)
BitTorrent::Session::instance()->addTorrent(torrentSource, params.torrentParams);
BitTorrent::Session::instance()->addTorrent(torrentSource, params.addTorrentParams);
}
}
int Application::exec(const QStringList &params)
int Application::exec()
try
{
#if !defined(DISABLE_WEBUI) && defined(DISABLE_GUI)
@ -870,13 +909,14 @@ try
#endif // DISABLE_WEBUI
m_isProcessingParamsAllowed = true;
for (const AddTorrentParams &params : m_paramsQueue)
for (const QBtCommandLineParameters &params : m_paramsQueue)
processParams(params);
m_paramsQueue.clear();
});
if (!params.isEmpty())
m_paramsQueue.append(parseParams(params));
const QBtCommandLineParameters params = commandLineArgs();
if (!params.torrentSources.isEmpty())
m_paramsQueue.append(params);
return BaseApplication::exec();
}
@ -962,7 +1002,8 @@ bool Application::event(QEvent *ev)
path = static_cast<QFileOpenEvent *>(ev)->url().toString();
qDebug("Received a mac file open event: %s", qUtf8Printable(path));
const AddTorrentParams params = parseParams({path});
QBtCommandLineParameters params;
params.torrentSources.append(path);
// If Application is not allowed to process params immediately
// (i.e., other components are not ready) store params
if (m_isProcessingParamsAllowed)