diff --git a/sources/ui/configpage/generalconfigurationpage.cpp b/sources/ui/configpage/generalconfigurationpage.cpp index 05688b006..6dd1916e8 100644 --- a/sources/ui/configpage/generalconfigurationpage.cpp +++ b/sources/ui/configpage/generalconfigurationpage.cpp @@ -395,9 +395,6 @@ void GeneralConfigurationPage::applyConf() if (!ui->m_live_assistant->isChecked()) LiveServer::instance().stop(); #endif } - //What an assistant reads about this QElectroTech follows the change - AssistantInfo::write(); - //GENERIC PANEL settings.setValue("genericpanel/folio",ui->m_use_folio_label->isChecked()); @@ -565,6 +562,12 @@ void GeneralConfigurationPage::applyConf() diagram->update(); } } + + //What an assistant reads about this QElectroTech follows the + //change. Written last: the collection and title block paths are + //applied above, and an assistant launching a headless run takes + //the user and company collections from this file. + AssistantInfo::write(); } /** diff --git a/tests/qttest/CMakeLists.txt b/tests/qttest/CMakeLists.txt index 1304bc356..3f7487f28 100644 --- a/tests/qttest/CMakeLists.txt +++ b/tests/qttest/CMakeLists.txt @@ -267,6 +267,10 @@ endfunction() # alone and with a group. qet_add_app_test(tst_rotateselectionimage tst_rotateselectionimage.cpp) +# Accepting the settings dialog writes qet-assistant.json with the +# collection paths just chosen, not the ones they replace. +qet_add_app_test(tst_assistantinfopaths tst_assistantinfopaths.cpp) + # Escape during a picture's resize, rotate or pivot drag puts it back, keeps # it selected and records no undo step (#1414); the key goes to the view. qet_add_app_test(tst_imagehandleescape tst_imagehandleescape.cpp) diff --git a/tests/qttest/tst_assistantinfopaths.cpp b/tests/qttest/tst_assistantinfopaths.cpp new file mode 100644 index 000000000..96e99dd67 --- /dev/null +++ b/tests/qttest/tst_assistantinfopaths.cpp @@ -0,0 +1,100 @@ +/* + Copyright 2006-2026 The QElectroTech Team + This file is part of QElectroTech. + + QElectroTech 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 2 of the License, or + (at your option) any later version. + + QElectroTech 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 QElectroTech. If not, see . +*/ +#include "qetapptest.h" +#include "scripting/assistantinfo.h" +#include "ui/configpage/generalconfigurationpage.h" + +#include +#include +#include +#include +#include +#include +#include + +/** + qet-assistant.json names the user and company collections, and the qet + MCP server hands them to every headless run it starts. Accepting the + settings dialog wrote the file before the dialog applied the new + collection paths, so the file kept the old ones: a company collection + chosen in the dialog stayed unknown to the assistant, and company:// + paths failed in its runs, until QElectroTech was started again. +*/ +class tst_assistantinfopaths : public QObject +{ + Q_OBJECT + + static QString writtenPath(const QString &key) + { + QFile file(AssistantInfo::path()); + if (!file.open(QIODevice::ReadOnly)) + return QString(); + const QJsonObject folders = QJsonDocument::fromJson(file.readAll()) + .object().value(QStringLiteral("folders")).toObject(); + return QDir::cleanPath(folders.value(key).toString()); + } + + static void choose(GeneralConfigurationPage &page, const QString &box, const QString &path) + { + auto *combo = page.findChild(box); + QVERIFY(combo); + //The state the page itself leaves once a folder is picked; + //signals blocked, or index 1 opens the folder dialog + const QSignalBlocker blocker(combo); + combo->setCurrentIndex(1); + combo->setItemData(1, path, Qt::DisplayRole); + } + +private slots: + void companyCollectionChosenInTheDialogIsWritten() + { + QTemporaryDir company; + QVERIFY(company.isValid()); + + GeneralConfigurationPage page; + choose(page, QStringLiteral("m_company_elmt_path_cb"), company.path()); + page.applyConf(); + + QCOMPARE(writtenPath(QStringLiteral("elements_company")), + QDir::cleanPath(company.path())); + } + + void customCollectionChosenInTheDialogIsWritten() + { + QTemporaryDir custom; + QVERIFY(custom.isValid()); + + GeneralConfigurationPage page; + choose(page, QStringLiteral("m_custom_elmt_path_cb"), custom.path()); + page.applyConf(); + + QCOMPARE(writtenPath(QStringLiteral("elements_custom")), + QDir::cleanPath(custom.path())); + } +}; + +int main(int argc, char **argv) +{ + //AssistantInfo writes to the standard data folder, whatever + //--data-dir says, and QETApp writes it as its editor opens: test + //mode from the very start keeps the user's own file out of reach. + QStandardPaths::setTestModeEnabled(true); + return QetAppTest::run(argc, argv); +} + +#include "tst_assistantinfopaths.moc"