diff options
| author | Andrei Golubev <andrei.golubev@qt.io> | 2022-07-01 15:53:48 +0200 |
|---|---|---|
| committer | Andrei Golubev <andrei.golubev@qt.io> | 2022-07-26 10:34:49 +0200 |
| commit | 9ec46f271a7adbc2d9f943695d9705fbd6afd393 (patch) | |
| tree | bd0ea58d5cd06a52a80df53bd00683ffe8e8c65e /src/qmlcompiler/qqmljsutils.cpp | |
| parent | ca68b0cde7a3b9bad468dfae1935d5886f461499 (diff) | |
Revise build to source dir mapping for QML tooling
Instead of doing build file path to source file path mapping for each
QML file, we could store qml module prefix to qml module output
directory mapping instead. This reduces the produced qrc size and makes
it more convenient to work with
Do a clean separation at the QQmlJSImporter level to prevent using
resource file mapper for build directory path resolution
Amends 7f567e6a424a3919337aad498543d58c1252df62
Change-Id: If984abada1d39c386af5712af778eb29956e0537
Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org>
Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Diffstat (limited to 'src/qmlcompiler/qqmljsutils.cpp')
| -rw-r--r-- | src/qmlcompiler/qqmljsutils.cpp | 44 |
1 files changed, 44 insertions, 0 deletions
diff --git a/src/qmlcompiler/qqmljsutils.cpp b/src/qmlcompiler/qqmljsutils.cpp index c07c0b6845..548c86eb67 100644 --- a/src/qmlcompiler/qqmljsutils.cpp +++ b/src/qmlcompiler/qqmljsutils.cpp @@ -146,3 +146,47 @@ std::optional<FixSuggestion> QQmlJSUtils::didYouMean(const QString &userInput, return {}; } } + +/*! \internal + + Returns a corresponding source directory path for \a buildDirectoryPath + Returns empty string on error +*/ +std::variant<QString, QQmlJS::DiagnosticMessage> +QQmlJSUtils::sourceDirectoryPath(const QQmlJSImporter *importer, const QString &buildDirectoryPath) +{ + const auto makeError = [](const QString &msg) { + return QQmlJS::DiagnosticMessage { msg, QtWarningMsg, QQmlJS::SourceLocation() }; + }; + + if (!importer->metaDataMapper()) + return makeError(u"QQmlJSImporter::metaDataMapper() is nullptr"_s); + + // for now, meta data contains just a single entry + QQmlJSResourceFileMapper::Filter matchAll { QString(), QStringList(), + QQmlJSResourceFileMapper::Directory + | QQmlJSResourceFileMapper::Recurse }; + QQmlJSResourceFileMapper::Entry entry = importer->metaDataMapper()->entry(matchAll); + if (!entry.isValid()) + return makeError(u"Failed to find meta data entry in QQmlJSImporter::metaDataMapper()"_s); + if (!buildDirectoryPath.startsWith(entry.filePath)) // assume source directory path already + return makeError(u"The module output directory does not match the build directory path"_s); + + QString qrcPath = buildDirectoryPath; + qrcPath.remove(0, entry.filePath.size()); + qrcPath.prepend(entry.resourcePath); + qrcPath.remove(0, 1); // remove extra "/" + + const QStringList sourceDirPaths = importer->resourceFileMapper()->filePaths( + QQmlJSResourceFileMapper::resourceFileFilter(qrcPath)); + if (sourceDirPaths.size() != 1) { + const QString matchedPaths = + sourceDirPaths.isEmpty() ? u"<none>"_s : sourceDirPaths.join(u", "); + return makeError( + QStringLiteral("QRC path %1 (deduced from %2) has unexpected number of mappings " + "(%3). File paths that matched:\n%4") + .arg(qrcPath, buildDirectoryPath, QString::number(sourceDirPaths.size()), + matchedPaths)); + } + return sourceDirPaths[0]; +} |
