Change error messages to reflect new module terminology
[profile/ivi/qtdeclarative.git] / tests / auto / qml / qqmlmoduleplugin / tst_qqmlmoduleplugin.cpp
index f6c1658..66b1505 100644 (file)
 #include "../../shared/testhttpserver.h"
 #include "../../shared/util.h"
 
-#define SERVER_ADDR "http://127.0.0.1:14450"
-#define SERVER_PORT 14450
+#define SERVER_ADDR "http://127.0.0.1:14456"
+#define SERVER_PORT 14456
 
+// Note: this test does not use module identifier directives in the qmldir files, because
+// it would result in repeated attempts to insert types into the same namespace.
+// This occurs because type registration is process-global, while the test
+// cases should really be run in proper per-process isolation.
 
 class tst_qqmlmoduleplugin : public QQmlDataTest
 {
@@ -72,17 +76,25 @@ private slots:
     void implicitQmldir_data();
     void importsNested();
     void importsNested_data();
+    void importLocalModule();
+    void importLocalModule_data();
+    void importStrictModule();
+    void importStrictModule_data();
 
 private:
     QString m_importsDirectory;
+    QString m_dataImportsDirectory;
 };
 
 void tst_qqmlmoduleplugin::initTestCase()
 {
     QQmlDataTest::initTestCase();
-    m_importsDirectory = directory() + QStringLiteral("/imports");
+    m_importsDirectory = QFINDTESTDATA(QStringLiteral("imports"));
     QVERIFY2(QFileInfo(m_importsDirectory).isDir(),
              qPrintable(QString::fromLatin1("Imports directory '%1' does not exist.").arg(m_importsDirectory)));
+    m_dataImportsDirectory = directory() + QStringLiteral("/imports");
+    QVERIFY2(QFileInfo(m_dataImportsDirectory).isDir(),
+             qPrintable(QString::fromLatin1("Imports directory '%1' does not exist.").arg(m_dataImportsDirectory)));
 }
 
 #define VERIFY_ERRORS(errorfile) \
@@ -129,6 +141,7 @@ void tst_qqmlmoduleplugin::importsPlugin()
     engine.addImportPath(m_importsDirectory);
     QTest::ignoreMessage(QtWarningMsg, "plugin created");
     QTest::ignoreMessage(QtWarningMsg, "import worked");
+    QTest::ignoreMessage(QtWarningMsg, "Module 'com.nokia.AutoTestQmlPluginType' does not contain a module identifier directive - it cannot be protected from external registrations.");
     QQmlComponent component(&engine, testFileUrl(QStringLiteral("works.qml")));
     foreach (QQmlError err, component.errors())
        qWarning() << err;
@@ -145,6 +158,7 @@ void tst_qqmlmoduleplugin::importsPlugin2()
     engine.addImportPath(m_importsDirectory);
     QTest::ignoreMessage(QtWarningMsg, "plugin2 created");
     QTest::ignoreMessage(QtWarningMsg, "import2 worked");
+    QTest::ignoreMessage(QtWarningMsg, "Module 'com.nokia.AutoTestQmlPluginType' does not contain a module identifier directive - it cannot be protected from external registrations.");
     QQmlComponent component(&engine, testFileUrl(QStringLiteral("works2.qml")));
     foreach (QQmlError err, component.errors())
         qWarning() << err;
@@ -161,6 +175,7 @@ void tst_qqmlmoduleplugin::importsPlugin21()
     engine.addImportPath(m_importsDirectory);
     QTest::ignoreMessage(QtWarningMsg, "plugin2.1 created");
     QTest::ignoreMessage(QtWarningMsg, "import2.1 worked");
+    QTest::ignoreMessage(QtWarningMsg, "Module 'com.nokia.AutoTestQmlPluginType' does not contain a module identifier directive - it cannot be protected from external registrations.");
     QQmlComponent component(&engine, testFileUrl(QStringLiteral("works21.qml")));
     foreach (QQmlError err, component.errors())
         qWarning() << err;
@@ -209,6 +224,8 @@ void tst_qqmlmoduleplugin::importPluginWithQmlFile()
     QQmlEngine engine;
     engine.addImportPath(path);
 
+    QTest::ignoreMessage(QtWarningMsg, "Module 'com.nokia.AutoTestPluginWithQmlFile' does not contain a module identifier directive - it cannot be protected from external registrations.");
+
     QQmlComponent component(&engine, testFileUrl(QStringLiteral("pluginWithQmlFile.qml")));
     foreach (QQmlError err, component.errors())
         qWarning() << err;
@@ -222,11 +239,11 @@ void tst_qqmlmoduleplugin::remoteImportWithQuotedUrl()
 {
     TestHTTPServer server(SERVER_PORT);
     QVERIFY(server.isValid());
-    server.serveDirectory(m_importsDirectory);
+    server.serveDirectory(m_dataImportsDirectory);
 
     QQmlEngine engine;
     QQmlComponent component(&engine);
-    component.setData("import \"http://127.0.0.1:14450/com/nokia/PureQmlModule\" \nComponentA { width: 300; ComponentB{} }", QUrl());
+    component.setData("import \"" SERVER_ADDR "/com/nokia/PureQmlModule\" \nComponentA { width: 300; ComponentB{} }", QUrl());
 
     QTRY_COMPARE(component.status(), QQmlComponent::Ready);
     QObject *object = component.create();
@@ -243,10 +260,10 @@ void tst_qqmlmoduleplugin::remoteImportWithUnquotedUri()
 {
     TestHTTPServer server(SERVER_PORT);
     QVERIFY(server.isValid());
-    server.serveDirectory(m_importsDirectory);
+    server.serveDirectory(m_dataImportsDirectory);
 
     QQmlEngine engine;
-    engine.addImportPath(m_importsDirectory);
+    engine.addImportPath(m_dataImportsDirectory);
     QQmlComponent component(&engine);
     component.setData("import com.nokia.PureQmlModule 1.0 \nComponentA { width: 300; ComponentB{} }", QUrl());
 
@@ -269,6 +286,8 @@ void tst_qqmlmoduleplugin::importsMixedQmlCppPlugin()
     QQmlEngine engine;
     engine.addImportPath(m_importsDirectory);
 
+    QTest::ignoreMessage(QtWarningMsg, "Module 'com.nokia.AutoTestQmlMixedPluginType' does not contain a module identifier directive - it cannot be protected from external registrations.");
+
     {
     QQmlComponent component(&engine, testFileUrl(QStringLiteral("importsMixedQmlCppPlugin.qml")));
 
@@ -308,6 +327,10 @@ void tst_qqmlmoduleplugin::versionNotInstalled()
     QQmlEngine engine;
     engine.addImportPath(m_importsDirectory);
 
+    static int count = 0;
+    if (++count == 1)
+        QTest::ignoreMessage(QtWarningMsg, "Module 'com.nokia.AutoTestQmlVersionPluginType' does not contain a module identifier directive - it cannot be protected from external registrations.");
+
     QQmlComponent component(&engine, testFileUrl(file));
     VERIFY_ERRORS(errorFile.toLatin1().constData());
 }
@@ -376,6 +399,10 @@ void tst_qqmlmoduleplugin::importsNested()
         QTest::ignoreMessage(QtWarningMsg, "QQmlComponent: Component is not ready");
     }
 
+    static int count = 0;
+    if (++count == 1)
+        QTest::ignoreMessage(QtWarningMsg, "Module 'com.nokia.AutoTestQmlNestedPluginType' does not contain a module identifier directive - it cannot be protected from external registrations.");
+
     QQmlComponent component(&engine, testFile(file));
     QObject *obj = component.create();
 
@@ -391,6 +418,126 @@ void tst_qqmlmoduleplugin::importsNested()
     }
 }
 
+void tst_qqmlmoduleplugin::importLocalModule()
+{
+    QFETCH(QString, qml);
+    QFETCH(int, majorVersion);
+    QFETCH(int, minorVersion);
+
+    QQmlEngine engine;
+    QQmlComponent component(&engine);
+    component.setData(qml.toUtf8(), testFileUrl("empty.qml"));
+
+    QScopedPointer<QObject> object(component.create());
+    QVERIFY(object != 0);
+    QCOMPARE(object->property("majorVersion").value<int>(), majorVersion);
+    QCOMPARE(object->property("minorVersion").value<int>(), minorVersion);
+}
+
+void tst_qqmlmoduleplugin::importLocalModule_data()
+{
+    QTest::addColumn<QString>("qml");
+    QTest::addColumn<int>("majorVersion");
+    QTest::addColumn<int>("minorVersion");
+
+    QTest::newRow("default version")
+        << "import \"localModule\"\n"
+           "TestComponent {}"
+        << 2 << 0;
+
+    QTest::newRow("specific version")
+        << "import \"localModule\" 1.1\n"
+           "TestComponent {}"
+        << 1 << 1;
+
+    QTest::newRow("lesser version")
+        << "import \"localModule\" 1.0\n"
+           "TestComponent {}"
+        << 1 << 0;
+
+    // Note: this does not match the behaviour of installed modules, which fail for this case:
+    QTest::newRow("nonexistent version")
+        << "import \"localModule\" 1.3\n"
+           "TestComponent {}"
+        << 1 << 1;
+
+    QTest::newRow("high version")
+        << "import \"localModule\" 2.0\n"
+           "TestComponent {}"
+        << 2 << 0;
+}
+
+void tst_qqmlmoduleplugin::importStrictModule()
+{
+    QFETCH(QString, qml);
+    QFETCH(QString, warning);
+    QFETCH(QString, error);
+
+    if (!warning.isEmpty())
+        QTest::ignoreMessage(QtWarningMsg, qPrintable(warning));
+
+    QQmlEngine engine;
+    engine.addImportPath(m_importsDirectory);
+
+    QUrl url(testFileUrl("empty.qml"));
+
+    QQmlComponent component(&engine);
+    component.setData(qml.toUtf8(), url);
+
+    if (error.isEmpty()) {
+        QScopedPointer<QObject> object(component.create());
+        QVERIFY(object != 0);
+    } else {
+        QVERIFY(!component.isReady());
+        QCOMPARE(component.errors().count(), 1);
+        QCOMPARE(component.errors().first().toString(), url.toString() + error);
+    }
+}
+
+void tst_qqmlmoduleplugin::importStrictModule_data()
+{
+    QTest::addColumn<QString>("qml");
+    QTest::addColumn<QString>("warning");
+    QTest::addColumn<QString>("error");
+
+    QTest::newRow("success")
+        << "import com.nokia.StrictModule 1.0\n"
+           "MyPluginType {}"
+        << QString()
+        << QString();
+
+    QTest::newRow("wrong target")
+        << "import com.nokia.InvalidStrictModule 1.0\n"
+           "MyPluginType {}"
+        << QString()
+        << ":1:1: plugin cannot be loaded for module \"com.nokia.InvalidStrictModule\": Cannot install element 'MyPluginType' into unregistered namespace 'com.nokia.SomeOtherModule'";
+
+    QTest::newRow("non-strict clash")
+        << "import com.nokia.NonstrictModule 1.0\n"
+           "MyPluginType {}"
+        << "Module 'com.nokia.NonstrictModule' does not contain a module identifier directive - it cannot be protected from external registrations."
+        << ":1:1: plugin cannot be loaded for module \"com.nokia.NonstrictModule\": Cannot install element 'MyPluginType' into protected namespace 'com.nokia.StrictModule'";
+
+    QTest::newRow("non-strict preemption")
+        << "import com.nokia.PreemptiveModule 1.0\n"
+           "import com.nokia.PreemptedStrictModule 1.0\n"
+           "MyPluginType {}"
+        << "Module 'com.nokia.PreemptiveModule' does not contain a module identifier directive - it cannot be protected from external registrations."
+        << ":2:1: plugin cannot be loaded for module \"com.nokia.PreemptedStrictModule\": Namespace 'com.nokia.PreemptedStrictModule' has already been used for type registration";
+
+    QTest::newRow("invalid namespace")
+        << "import com.nokia.InvalidNamespaceModule 1.0\n"
+           "MyPluginType {}"
+        << QString()
+        << ":1:1: plugin cannot be loaded for module \"com.nokia.InvalidNamespaceModule\": Module namespace 'com.nokia.AwesomeModule' does not match import URI 'com.nokia.InvalidNamespaceModule'";
+
+    QTest::newRow("module directive must be first")
+        << "import com.nokia.InvalidFirstCommandModule 1.0\n"
+           "MyPluginType {}"
+        << QString()
+        << ":1:1: module identifier directive must be the first command in a qmldir file";
+}
+
 QTEST_MAIN(tst_qqmlmoduleplugin)
 
 #include "tst_qqmlmoduleplugin.moc"