From 4a654c38c0ab4bf74ee933bd336d33458fbc191a Mon Sep 17 00:00:00 2001 From: Felix Kauselmann Date: Fri, 28 Aug 2020 08:27:22 +0200 Subject: [PATCH] Headless server: Add support for setting a port from commandline Manual editing of a config file for setting a port is not ideal. Solution: add a set-port command to save a port and also a --port option to allow setting a temporary port during startup --- CHANGELOG.md | 3 ++ YACReaderLibrary/server/startup.cpp | 30 +++++-------------- YACReaderLibrary/server/startup.h | 2 +- YACReaderLibraryServer/main.cpp | 46 +++++++++++++++++++++++++++-- 4 files changed, 54 insertions(+), 27 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 56e34450..7d1dca92 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -13,6 +13,9 @@ Version counting is based on semantic versioning (Major.Feature.Patch) * fix object leaks in database code * add bidirectional sync support +### YACReaderLibraryServer +* add support for port setting from the commandline + ## 9.6.0 ### Reader and Library * RAR5 support. diff --git a/YACReaderLibrary/server/startup.cpp b/YACReaderLibrary/server/startup.cpp index be42e3e2..93781a1c 100644 --- a/YACReaderLibrary/server/startup.cpp +++ b/YACReaderLibrary/server/startup.cpp @@ -32,34 +32,12 @@ using stefanfrings::HttpSessionStore; using stefanfrings::StaticFileController; using stefanfrings::TemplateCache; -void Startup::start() +void Startup::start(quint16 port) { // Initialize the core application QCoreApplication *app = QCoreApplication::instance(); QString configFileName = YACReader::getSettingsPath() + "/" + QCoreApplication::applicationName() + ".ini"; - /* - // Configure logging into files - QSettings* mainLogSettings=new QSettings(configFileName,QSettings::IniFormat,app); - mainLogSettings->beginGroup("mainLogFile"); - //QSettings* debugLogSettings=new QSettings(configFileName,QSettings::IniFormat,app); - //debugLogSettings->beginGroup("debugLogFile"); - - if(mainLogSettings->value("fileName").isNull()) - mainLogSettings->setValue("fileName", QFileInfo(YACReader::getSettingsPath(), "server_log.log").absoluteFilePath()); - - if(mainLogSettings->value("maxSize").isNull()) - mainLogSettings->setValue("maxSize",1048576); - - if(mainLogSettings->value("maxBackups").isNull()) - mainLogSettings->setValue("maxBackups",1); - - if(mainLogSettings->value("minLevel").isNull()) - mainLogSettings->setValue("minLevel",QtCriticalMsg); - - Logger* logger=new FileLogger(mainLogSettings,10000,app); - logger->installMsgHandler();*/ - // Configure template loader and cache auto templateSettings = new QSettings(configFileName, QSettings::IniFormat, app); templateSettings->beginGroup("templates"); @@ -134,6 +112,12 @@ void Startup::start() listener = new HttpListener(listenerSettings, new RequestMapper(app), app); + if (port != 0) { + if (listener->isListening()) { + listener->close(); + } + listener->QTcpServer::listen(QHostAddress::Any, port); + } // if the requested port is busy, use random port if (!listener->isListening()) { listener->QTcpServer::listen(QHostAddress::Any, 0); diff --git a/YACReaderLibrary/server/startup.h b/YACReaderLibrary/server/startup.h index e8dfc7cc..dcbb20aa 100644 --- a/YACReaderLibrary/server/startup.h +++ b/YACReaderLibrary/server/startup.h @@ -26,7 +26,7 @@ public: /** Constructor */ Startup(); /** Start the server */ - void start(); + void start(quint16 port = 0); /** Stop the server */ void stop(); diff --git a/YACReaderLibraryServer/main.cpp b/YACReaderLibraryServer/main.cpp index e18ca87b..32f62319 100644 --- a/YACReaderLibraryServer/main.cpp +++ b/YACReaderLibraryServer/main.cpp @@ -109,8 +109,9 @@ int main(int argc, char **argv) parser.setApplicationDescription(QCoreApplication::tr("\nYACReaderLibraryServer is the headless (no gui) version of YACReaderLibrary")); parser.addHelpOption(); const QCommandLineOption versionOption = parser.addVersionOption(); - parser.addPositionalArgument("command", "The command to execute. [start, create-library, update-library, add-library, remove-library, list-libraries]"); + parser.addPositionalArgument("command", "The command to execute. [start, create-library, update-library, add-library, remove-library, list-libraries, set-port]"); parser.addOption({ "loglevel", "Set log level. Valid values: trace, info, debug, warn, error.", "loglevel", "info" }); + parser.addOption({ "port", "Set server port (temporary). Valid values: 1-65535", "port" }); parser.parse(app.arguments()); const QStringList args = parser.positionalArguments(); @@ -179,13 +180,26 @@ int main(int argc, char **argv) //server Startup *s = new Startup(); - s->start(); + if (parser.isSet("port")) { + bool valid; + qint32 port = parser.value("port").toInt(&valid); + if (!valid || port < 1 || port > 65535) { + qout << "Error: " << parser.value("port") << " is not a valid port" << endl; + parser.showHelp(); + return 0; + } else { + s->start(port); + } + + } else { + s->start(); + } QLOG_INFO() << "YACReaderLibraryServer attempting to start"; logSystemAndConfig(); - if (YACReaderLocalServer::isRunning()) //s�lo se permite una instancia de YACReaderLibrary + if (YACReaderLocalServer::isRunning()) // allow one server instance { QLOG_WARN() << "another instance of YACReaderLibrary is running"; #ifdef Q_OS_WIN @@ -194,6 +208,7 @@ int main(int argc, char **argv) return 0; } QLOG_INFO() << "YACReaderLibrary starting"; + QLOG_INFO() << "Running on port" << s->getPort(); //Update libraries to now versions LibrariesUpdater updater; @@ -290,6 +305,31 @@ int main(int argc, char **argv) qout << libraryName << " : " << libraries.getPath(libraryName) << endl; return 0; + } else if (command == "set-port") { + parser.clearPositionalArguments(); + parser.addPositionalArgument("set-port", "Set server port (persistent)."); + parser.addPositionalArgument("port", "1-65535", ""); + parser.process(app); + + const QStringList args = parser.positionalArguments(); + if (args.length() != 2) { + parser.showHelp(); + return 0; + } + + bool valid; + qint32 port = args.at(1).toInt(&valid); + if (!valid || port < 1 || port > 65535) { + qout << "Invalid server port"; + parser.showHelp(); + return 0; + } + + QSettings *settings = new QSettings(YACReader::getSettingsPath() + "/" + QCoreApplication::applicationName() + ".ini", QSettings::IniFormat); + settings->setValue("listener/port", QString::number(port)); + delete settings; + return 0; + } else //error { parser.process(app);