From 308f508c7ef2c4cdc3849f614c942b485c97eb17 Mon Sep 17 00:00:00 2001 From: Adriaan de Groot Date: Mon, 26 Feb 2018 14:29:26 +0100 Subject: [PATCH] [calamares] Add a test-application. This test-application should load a single module and execute it -- that can be used to quickly test configurations, loading, etc. This is preparation for loading all sorts of Python modules by PythonQt. The loader does some internals initialization and gets the module, but doesn't actually run it yet. --- src/calamares/CMakeLists.txt | 6 ++ src/calamares/testmain.cpp | 153 +++++++++++++++++++++++++++++++++++ 2 files changed, 159 insertions(+) create mode 100644 src/calamares/testmain.cpp diff --git a/src/calamares/CMakeLists.txt b/src/calamares/CMakeLists.txt index 270abbb88..e1f8e4236 100644 --- a/src/calamares/CMakeLists.txt +++ b/src/calamares/CMakeLists.txt @@ -68,3 +68,9 @@ install( FILES ${CMAKE_SOURCE_DIR}/data/images/squid.svg RENAME calamares.svg DESTINATION ${CMAKE_INSTALL_DATADIR}/icons/hicolor/scalable/apps ) + +if( BUILD_TESTING ) + add_executable( loadmodule testmain.cpp ) + target_link_libraries( loadmodule ${CALAMARES_LIBRARIES} Qt5::Core Qt5::Widgets calamaresui ) + # Don't install, it's just for enable_testing +endif() diff --git a/src/calamares/testmain.cpp b/src/calamares/testmain.cpp new file mode 100644 index 000000000..dfd6ed7eb --- /dev/null +++ b/src/calamares/testmain.cpp @@ -0,0 +1,153 @@ +/* === This file is part of Calamares - === + * + * Copyright 2018, Adriaan de Groot + * + * Calamares is free software: you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation, either version 3 of the License, or + * (at your option) any later version. + * + * Calamares is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with Calamares. If not, see . + */ + +/* + * This executable loads and runs a Calamares Python module + * within a C++ application, in order to test the different + * bindings. + */ + +#include "utils/Logger.h" +#include "utils/YamlUtils.h" +#include "modulesystem/Module.h" + +#include "Settings.h" + +#include +#include +#include +#include + +#include + +static QString +handle_args( QCoreApplication& a ) +{ + QCommandLineOption debugLevelOption( QStringLiteral("D"), + "Verbose output for debugging purposes (0-8).", "level" ); + + QCommandLineParser parser; + parser.setApplicationDescription( "Calamares module tester" ); + parser.addHelpOption(); + parser.addVersionOption(); + + parser.addOption( debugLevelOption ); + parser.addPositionalArgument( "module", "Path or name of module to run." ); + + parser.process( a ); + + if ( parser.isSet( debugLevelOption ) ) + { + bool ok = true; + int l = parser.value( debugLevelOption ).toInt( &ok ); + unsigned int dlevel = 0; + if ( !ok || ( l < 0 ) ) + dlevel = Logger::LOGVERBOSE; + else + dlevel = l; + Logger::setupLogLevel( dlevel ); + } + + const QStringList args = parser.positionalArguments(); + if ( args.isEmpty() ) + { + cError() << "Missing path.\n"; + parser.showHelp(); + return QString(); // NOTREACHED + } + if ( args.size() > 1 ) + { + cError() << "More than one path.\n"; + parser.showHelp(); + return QString(); // NOTREACHED + } + + return args.first(); +} + + +static Calamares::Module* +load_module( const QString& moduleName ) +{ + QFileInfo fi; + + bool ok = false; + QVariantMap descriptor; + + for ( const QString& prefix : QStringList{ "./", "src/modules/", "modules/" } ) + { + // Could be a complete path, eg. src/modules/dummycpp/module.desc + fi = QFileInfo( prefix + moduleName ); + if ( fi.exists() && fi.isFile() ) + descriptor = CalamaresUtils::loadYaml( fi, &ok ); + if ( ok ) + break; + + // Could be a path without module.desc + fi = QFileInfo( prefix + moduleName ); + if ( fi.exists() && fi.isDir() ) + { + fi = QFileInfo( prefix + moduleName + "/module.desc" ); + if ( fi.exists() && fi.isFile() ) + descriptor = CalamaresUtils::loadYaml( fi, &ok ); + if ( ok ) break; + } + } + + if ( !ok ) + { + cWarning() << "No suitable module descriptor found."; + return nullptr; + } + + QString name = descriptor.value( "name" ).toString(); + if ( name.isEmpty() ) + { + cWarning() << "No name found in module descriptor" << fi.absoluteFilePath(); + return nullptr; + } + + QString moduleDirectory = fi.absolutePath(); + QString configFile = moduleDirectory + '/' + name + ".conf"; + + Calamares::Module* module = Calamares::Module::fromDescriptor( + descriptor, name, configFile, moduleDirectory ); + + return module; +} + +int +main( int argc, char* argv[] ) +{ + QCoreApplication a( argc, argv ); + + QString module = handle_args( a ); + if ( module.isEmpty() ) + return 1; + + std::unique_ptr< Calamares::Settings > settings_p( new Calamares::Settings( QString(), true ) ); + cDebug() << "Calamares test module-loader" << module; + Calamares::Module* m = load_module( module ); + if ( !m ) + { + cError() << "No module.desc data found in" << module; + return 1; + } + + return 0; +}