diff options
-rw-r--r-- | src/qmlcompiler/qqmljsimportvisitor.cpp | 17 | ||||
-rw-r--r-- | src/qmlcompiler/qqmljsimportvisitor_p.h | 4 | ||||
-rw-r--r-- | tests/auto/qml/qmltc_qprocess/CMakeLists.txt | 1 | ||||
-rw-r--r-- | tests/auto/qml/qmltc_qprocess/data/customParsed.qml | 7 | ||||
-rw-r--r-- | tests/auto/qml/qmltc_qprocess/tst_qmltc_qprocess.cpp | 16 | ||||
-rw-r--r-- | tools/qmltc/main.cpp | 8 | ||||
-rw-r--r-- | tools/qmltc/qmltcvisitor.cpp | 7 | ||||
-rw-r--r-- | tools/qmltc/qmltcvisitor.h | 5 |
8 files changed, 57 insertions, 8 deletions
diff --git a/src/qmlcompiler/qqmljsimportvisitor.cpp b/src/qmlcompiler/qqmljsimportvisitor.cpp index 6ac9a73a61..7af1cff209 100644 --- a/src/qmlcompiler/qqmljsimportvisitor.cpp +++ b/src/qmlcompiler/qqmljsimportvisitor.cpp @@ -603,7 +603,7 @@ void QQmlJSImportVisitor::processDefaultProperties() QQmlJSScope::ConstPtr parentScope = it.key(); // We can't expect custom parser default properties to be sensible, discard them for now. - if (parentScope->isInCustomParserParent()) + if (checkCustomParser(parentScope)) continue; /* consider: @@ -1071,7 +1071,7 @@ void QQmlJSImportVisitor::processPropertyBindings() // These warnings do not apply for custom parsers and their children and need to be // handled on a case by case basis - if (scope->isInCustomParserParent()) + if (checkCustomParser(scope)) continue; // TODO: Can this be in a better suited category? @@ -1273,7 +1273,7 @@ void QQmlJSImportVisitor::addDefaultProperties() m_pendingDefaultProperties[m_currentScope->parentScope()] << m_currentScope; - if (parentScope->isInCustomParserParent()) + if (checkCustomParser(parentScope)) return; /* consider: @@ -1370,7 +1370,7 @@ void QQmlJSImportVisitor::checkGroupedAndAttachedScopes(QQmlJSScope::ConstPtr sc { // These warnings do not apply for custom parsers and their children and need to be handled on a // case by case basis - if (scope->isInCustomParserParent()) + if (checkCustomParser(scope)) return; auto children = scope->childScopes(); @@ -1396,6 +1396,11 @@ void QQmlJSImportVisitor::checkGroupedAndAttachedScopes(QQmlJSScope::ConstPtr sc } } +bool QQmlJSImportVisitor::checkCustomParser(const QQmlJSScope::ConstPtr &scope) +{ + return scope->isInCustomParserParent(); +} + void QQmlJSImportVisitor::flushPendingSignalParameters() { const QQmlJSMetaSignalHandler handler = m_signalHandlers[m_pendingSignalHandler]; @@ -2390,7 +2395,7 @@ void QQmlJSImportVisitor::endVisit(UiArrayBinding *arrayBinding) const auto propertyName = getScopeName(m_currentScope, QQmlSA::ScopeType::QMLScope); leaveEnvironment(); - if (m_currentScope->isInCustomParserParent()) { + if (checkCustomParser(m_currentScope)) { // These warnings do not apply for custom parsers and their children and need to be handled // on a case by case basis return; @@ -2951,7 +2956,7 @@ void QQmlJSImportVisitor::endVisit(QQmlJS::AST::UiObjectBinding *uiob) } } - if (m_currentScope->isInCustomParserParent()) { + if (checkCustomParser(m_currentScope)) { // These warnings do not apply for custom parsers and their children and need to be handled // on a case by case basis } else { diff --git a/src/qmlcompiler/qqmljsimportvisitor_p.h b/src/qmlcompiler/qqmljsimportvisitor_p.h index abaca7a691..c56f6a9f99 100644 --- a/src/qmlcompiler/qqmljsimportvisitor_p.h +++ b/src/qmlcompiler/qqmljsimportvisitor_p.h @@ -159,6 +159,8 @@ protected: void throwRecursionDepthError() override; + virtual bool checkCustomParser(const QQmlJSScope::ConstPtr &scope); + QString m_implicitImportDirectory; QStringList m_qmldirFiles; QQmlJSScope::Ptr m_currentScope; @@ -266,7 +268,7 @@ protected: template<typename ErrorHandler> bool checkTypeResolved(const QQmlJSScope::ConstPtr &type, ErrorHandler handle) { - if (type->isFullyResolved() || type->isInCustomParserParent()) + if (type->isFullyResolved() || checkCustomParser(type)) return true; // Note: ignore duplicates, but only after we are certain that the type diff --git a/tests/auto/qml/qmltc_qprocess/CMakeLists.txt b/tests/auto/qml/qmltc_qprocess/CMakeLists.txt index bcde6ac3bb..0145c48657 100644 --- a/tests/auto/qml/qmltc_qprocess/CMakeLists.txt +++ b/tests/auto/qml/qmltc_qprocess/CMakeLists.txt @@ -48,6 +48,7 @@ qt6_add_qml_module(tst_qmltc_qprocess data/componentDefinitionInnerRequiredProperty.qml data/componentDefinitionInnerRequiredPropertyFromOutside.qml data/innerLevelRequiredProperty.qml + data/customParsed.qml NO_GENERATE_EXTRA_QMLDIRS ) diff --git a/tests/auto/qml/qmltc_qprocess/data/customParsed.qml b/tests/auto/qml/qmltc_qprocess/data/customParsed.qml new file mode 100644 index 0000000000..c33aa2f0c8 --- /dev/null +++ b/tests/auto/qml/qmltc_qprocess/data/customParsed.qml @@ -0,0 +1,7 @@ +import QtQuick + +Item { + ListModel { + ListElement { a: 5 } + } +} diff --git a/tests/auto/qml/qmltc_qprocess/tst_qmltc_qprocess.cpp b/tests/auto/qml/qmltc_qprocess/tst_qmltc_qprocess.cpp index 0caff18ebf..13b2caa330 100644 --- a/tests/auto/qml/qmltc_qprocess/tst_qmltc_qprocess.cpp +++ b/tests/auto/qml/qmltc_qprocess/tst_qmltc_qprocess.cpp @@ -58,6 +58,7 @@ private slots: void componentDefinitionInnerRequiredProperty(); void componentDefinitionInnerRequiredPropertyFromOutside(); void innerLevelRequiredProperty(); + void customParsed(); }; #ifndef TST_QMLTC_QPROCESS_RESOURCES @@ -364,5 +365,20 @@ void tst_qmltc_qprocess::innerLevelRequiredProperty() } } +void tst_qmltc_qprocess::customParsed() +{ + const auto errors = runQmltc(u"customParsed.qml"_s, false); + QVERIFY(errors.contains( + u"customParsed.qml:5:9: Cannot assign to non-existent default property [missing-property]" + )); + QVERIFY(errors.contains( + u"customParsed.qml:5:23: Could not find property \"a\". [missing-property]" + )); + QVERIFY(errors.contains( + u"customParsed.qml:: qmltc does not support custom parsers such as ListModel or old forms " + "of Connections and PropertyChanges. [compiler]" + )); +} + QTEST_MAIN(tst_qmltc_qprocess) #include "tst_qmltc_qprocess.moc" diff --git a/tools/qmltc/main.cpp b/tools/qmltc/main.cpp index 3d412182ea..afc9cf95dc 100644 --- a/tools/qmltc/main.cpp +++ b/tools/qmltc/main.cpp @@ -291,8 +291,14 @@ int main(int argc, char **argv) QString(), QString(), QString()); passMan->analyze(QQmlJSScope::createQQmlSAElement(visitor.result())); - if (logger.hasErrors()) + if (logger.hasErrors()) { + if (visitor.hasSeenCustomParsers()) { + logger.log(QStringLiteral("qmltc does not support custom parsers such as ListModel or " + "old forms of Connections and PropertyChanges."), + qmlCompiler, QQmlJS::SourceLocation()); + } return EXIT_FAILURE; + } QList<QQmlJS::DiagnosticMessage> warnings = importer.takeGlobalWarnings(); if (!warnings.isEmpty()) { diff --git a/tools/qmltc/qmltcvisitor.cpp b/tools/qmltc/qmltcvisitor.cpp index dee3426598..2d1c61bc19 100644 --- a/tools/qmltc/qmltcvisitor.cpp +++ b/tools/qmltc/qmltcvisitor.cpp @@ -337,6 +337,13 @@ void QmltcVisitor::endVisit(QQmlJS::AST::UiProgram *program) checkNamesAndTypes(type); } +bool QmltcVisitor::checkCustomParser(const QQmlJSScope::ConstPtr &scope) +{ + if (QQmlJSImportVisitor::checkCustomParser(scope)) + m_seenCustomParsers = true; + return false; +} + QQmlJSScope::ConstPtr fetchType(const QQmlJSMetaPropertyBinding &binding) { switch (binding.bindingType()) { diff --git a/tools/qmltc/qmltcvisitor.h b/tools/qmltc/qmltcvisitor.h index b96c19063f..42b220ed97 100644 --- a/tools/qmltc/qmltcvisitor.h +++ b/tools/qmltc/qmltcvisitor.h @@ -135,6 +135,9 @@ public: enum Mode { Import, Compile }; void setMode(Mode mode) { m_mode = mode; } + bool checkCustomParser(const QQmlJSScope::ConstPtr &scope) override; + bool hasSeenCustomParsers() const { return m_seenCustomParsers; } + protected: QStringList m_qmlTypeNames; // names of QML types arranged as a stack QHash<QString, int> m_qmlTypeNameCounts; @@ -184,6 +187,8 @@ protected: QHash<QQmlJSScope::ConstPtr, int> m_typesWithId; Mode m_mode = Mode::Import; + + bool m_seenCustomParsers = false; }; QT_END_NAMESPACE |