Limit case-sensitivity check in QML to file names.
authorFriedemann Kleint <Friedemann.Kleint@digia.com>
Thu, 29 Nov 2012 16:20:34 +0000 (17:20 +0100)
committerThe Qt Project <gerrit-noreply@qt-project.org>
Fri, 30 Nov 2012 14:21:38 +0000 (15:21 +0100)
Provide for checking relative paths only; default to file names.
Currently, the checking triggers on a drive letters and
installation folder names, which is too strict.

Task-number: QTBUG-28277
Change-Id: I1174bb0c485eeb1ffee10bb2a523d6629c57728b
Reviewed-by: Kai Koehne <kai.koehne@digia.com>
src/qml/qml/qqmlengine.cpp
src/qml/qml/qqmlglobal_p.h
tests/auto/qml/qqmllanguage/tst_qqmllanguage.cpp

index 9db8927..2a46cdb 100644 (file)
@@ -2078,7 +2078,7 @@ bool QQmlEnginePrivate::isScriptLoaded(const QUrl &url) const
     return typeLoader.isScriptLoaded(url);
 }
 
-bool QQml_isFileCaseCorrect(const QString &fileName)
+bool QQml_isFileCaseCorrect(const QString &fileName, int lengthIn /* = -1 */)
 {
 #if defined(Q_OS_MAC) || defined(Q_OS_WIN)
     QFileInfo info(fileName);
@@ -2100,7 +2100,21 @@ bool QQml_isFileCaseCorrect(const QString &fileName)
     const int absoluteLength = absolute.length();
     const int canonicalLength = canonical.length();
 
-    const int length = qMin(absoluteLength, canonicalLength);
+    int length = qMin(absoluteLength, canonicalLength);
+    if (lengthIn >= 0) {
+        length = qMin(lengthIn, length);
+    } else {
+        // No length given: Limit to file name. Do not trigger
+        // on drive letters or folder names.
+        int lastSlash = absolute.lastIndexOf(QLatin1Char('/'));
+        if (lastSlash < 0)
+            lastSlash = absolute.lastIndexOf(QLatin1Char('\\'));
+        if (lastSlash >= 0) {
+            const int fileNameLength = absoluteLength - 1 - lastSlash;
+            length = qMin(length, fileNameLength);
+        }
+    }
+
     for (int ii = 0; ii < length; ++ii) {
         const QChar &a = absolute.at(absoluteLength - 1 - ii);
         const QChar &c = canonical.at(canonicalLength - 1 - ii);
@@ -2111,6 +2125,7 @@ bool QQml_isFileCaseCorrect(const QString &fileName)
             return false;
     }
 #else
+    Q_UNUSED(lengthIn)
     Q_UNUSED(fileName)
 #endif
     return true;
index 037323d..9de7e8f 100644 (file)
@@ -204,8 +204,15 @@ struct QQmlGraphics_DerivedObject : public QObject
     It may have false positives (say the case is correct when it isn't), but it
     should never have a false negative (say the case is incorrect when it is 
     correct).
+
+    Length specifies specifies the number of characters to be checked from
+    behind. That is, if a file name results from a relative path specification
+    like "foo/bar.qml" and is made absolute, the original length (11) should
+    be passed indicating that only the last part of the relative path should
+    be checked.
+
 */
-bool QQml_isFileCaseCorrect(const QString &fileName);
+bool QQml_isFileCaseCorrect(const QString &fileName, int length = -1);
 
 /*!
     Makes the \a object a child of \a parent.  Note that when using this method,
index 138a263..cf6c834 100644 (file)
@@ -2482,15 +2482,16 @@ void tst_qqmllanguage::importIncorrectCase()
     if (engine.importPathList() == defaultImportPathList)
         engine.addImportPath(testFile("lib"));
 
-    QQmlComponent component(&engine, testFileUrl("importIncorrectCase.qml"));
+    // Load "importIncorrectCase.qml" using wrong case
+    QQmlComponent component(&engine, testFileUrl("ImportIncorrectCase.qml"));
 
     QList<QQmlError> errors = component.errors();
     QCOMPARE(errors.count(), 1);
 
-#if defined(Q_OS_MAC) || defined(Q_OS_WIN32)
-    QString expectedError = QLatin1String("cannot load module \"com.Nokia.installedtest\": File name case mismatch for \"") + testFile("lib/com/Nokia/installedtest/qmldir") + QLatin1String("\"");
+#if defined(Q_OS_MAC) || defined(Q_OS_WIN)
+    QString expectedError = QLatin1String("File name case mismatch");
 #else
-    QString expectedError = QLatin1String("module \"com.Nokia.installedtest\" is not installed");
+    QString expectedError = QLatin1String("File not found");
 #endif
 
     QCOMPARE(errors.at(0).description(), expectedError);