summaryrefslogtreecommitdiffstats
path: root/src/corelib
diff options
context:
space:
mode:
authorDavid Faure <david.faure@kdab.com>2020-09-11 10:05:51 +0200
committerDavid Faure <david.faure@kdab.com>2020-09-22 20:40:45 +0200
commitfc8f5afc874073f91d3770273e0a9164182d7897 (patch)
tree8cfd33f885ac7ee09d3e38bc18cdc343f435646b /src/corelib
parentad9108e2e96ebf67147a72a7dab00398ff637695 (diff)
QMimeDatabase: fix handling of glob-deleteall
Binary provider: It was not possible to remove the first glob in a local override, because the mainPattern handling would re-add the first glob back. XML provider: It didn't support glob-deleteall. Also, the order of the providers was wrong. We want to pick local overrides first, the internal DB has to go last in the list. Fixes: QTBUG-85436 Pick-to: 5.15 Change-Id: I9a4523f37cd962c730df9a6ed992bd01c075bf03 Reviewed-by: Thiago Macieira <thiago.macieira@intel.com>
Diffstat (limited to 'src/corelib')
-rw-r--r--src/corelib/mimetypes/qmimedatabase.cpp34
-rw-r--r--src/corelib/mimetypes/qmimeprovider.cpp1
-rw-r--r--src/corelib/mimetypes/qmimetypeparser.cpp7
-rw-r--r--src/corelib/mimetypes/qmimetypeparser_p.h1
4 files changed, 26 insertions, 17 deletions
diff --git a/src/corelib/mimetypes/qmimedatabase.cpp b/src/corelib/mimetypes/qmimedatabase.cpp
index 7a9bf2880d..56f5d471ea 100644
--- a/src/corelib/mimetypes/qmimedatabase.cpp
+++ b/src/corelib/mimetypes/qmimedatabase.cpp
@@ -101,27 +101,13 @@ void QMimeDatabasePrivate::loadProviders()
const auto fdoIterator = std::find_if(mimeDirs.constBegin(), mimeDirs.constEnd(), [](const QString &mimeDir) -> bool {
return QFileInfo::exists(mimeDir + QStringLiteral("/packages/freedesktop.org.xml")); }
);
+ const bool needInternalDB = QMimeXMLProvider::InternalDatabaseAvailable && fdoIterator == mimeDirs.constEnd();
//qDebug() << "mime dirs:" << mimeDirs;
Providers currentProviders;
std::swap(m_providers, currentProviders);
- if (QMimeXMLProvider::InternalDatabaseAvailable && fdoIterator == mimeDirs.constEnd()) {
- m_providers.reserve(mimeDirs.size() + 1);
- // Check if we already have a provider for the InternalDatabase
- const auto isInternal = [](const std::unique_ptr<QMimeProviderBase> &prov)
- {
- return prov && prov->isInternalDatabase();
- };
- const auto it = std::find_if(currentProviders.begin(), currentProviders.end(), isInternal);
- if (it == currentProviders.end()) {
- m_providers.push_back(Providers::value_type(new QMimeXMLProvider(this, QMimeXMLProvider::InternalDatabase)));
- } else {
- m_providers.push_back(std::move(*it));
- }
- } else {
- m_providers.reserve(mimeDirs.size());
- }
+ m_providers.reserve(mimeDirs.size() + (needInternalDB ? 1 : 0));
for (const QString &mimeDir : mimeDirs) {
const QString cacheFile = mimeDir + QStringLiteral("/mime.cache");
@@ -158,6 +144,21 @@ void QMimeDatabasePrivate::loadProviders()
m_providers.push_back(std::move(provider));
}
}
+ // mimeDirs is sorted "most local first, most global last"
+ // so the internal XML DB goes at the end
+ if (needInternalDB) {
+ // Check if we already have a provider for the InternalDatabase
+ const auto isInternal = [](const std::unique_ptr<QMimeProviderBase> &prov)
+ {
+ return prov && prov->isInternalDatabase();
+ };
+ const auto it = std::find_if(currentProviders.begin(), currentProviders.end(), isInternal);
+ if (it == currentProviders.end()) {
+ m_providers.push_back(Providers::value_type(new QMimeXMLProvider(this, QMimeXMLProvider::InternalDatabase)));
+ } else {
+ m_providers.push_back(std::move(*it));
+ }
+ }
}
const QMimeDatabasePrivate::Providers &QMimeDatabasePrivate::providers()
@@ -215,7 +216,6 @@ QStringList QMimeDatabasePrivate::mimeTypeForFileName(const QString &fileName)
QMimeGlobMatchResult QMimeDatabasePrivate::findByFileName(const QString &fileName)
{
QMimeGlobMatchResult result;
- // TODO this parses in the order (local, global). Check that it handles "NOGLOBS" correctly.
for (const auto &provider : providers())
provider->addFileNameMatches(fileName, result);
return result;
diff --git a/src/corelib/mimetypes/qmimeprovider.cpp b/src/corelib/mimetypes/qmimeprovider.cpp
index 7a6c522a9d..fcc6cdf088 100644
--- a/src/corelib/mimetypes/qmimeprovider.cpp
+++ b/src/corelib/mimetypes/qmimeprovider.cpp
@@ -542,6 +542,7 @@ void QMimeBinaryProvider::loadMimeTypePrivate(QMimeTypePrivate &data)
data.iconName = xml.attributes().value(QLatin1String("name")).toString();
} else if (tag == QLatin1String("glob-deleteall")) { // as written out by shared-mime-info >= 0.70
data.globPatterns.clear();
+ mainPattern.clear();
} else if (tag == QLatin1String("glob")) { // as written out by shared-mime-info >= 0.70
const QString pattern = xml.attributes().value(QLatin1String("pattern")).toString();
if (mainPattern.isEmpty() && pattern.startsWith(QLatin1Char('*'))) {
diff --git a/src/corelib/mimetypes/qmimetypeparser.cpp b/src/corelib/mimetypes/qmimetypeparser.cpp
index aa5427b16a..c874e5a6b4 100644
--- a/src/corelib/mimetypes/qmimetypeparser.cpp
+++ b/src/corelib/mimetypes/qmimetypeparser.cpp
@@ -63,6 +63,7 @@ static const char genericIconTagC[] = "generic-icon";
static const char iconTagC[] = "icon";
static const char nameAttributeC[] = "name";
static const char globTagC[] = "glob";
+static const char globDeleteAllTagC[] = "glob-deleteall";
static const char aliasTagC[] = "alias";
static const char patternAttributeC[] = "pattern";
static const char weightAttributeC[] = "weight";
@@ -123,6 +124,7 @@ QMimeTypeParserBase::ParseState QMimeTypeParserBase::nextState(ParseState curren
case ParseGenericIcon:
case ParseIcon:
case ParseGlobPattern:
+ case ParseGlobDeleteAll:
case ParseSubClass:
case ParseAlias:
case ParseOtherMimeTypeSubTag:
@@ -137,6 +139,8 @@ QMimeTypeParserBase::ParseState QMimeTypeParserBase::nextState(ParseState curren
return ParseIcon;
if (startElement == QLatin1String(globTagC))
return ParseGlobPattern;
+ if (startElement == QLatin1String(globDeleteAllTagC))
+ return ParseGlobDeleteAll;
if (startElement == QLatin1String(subClassTagC))
return ParseSubClass;
if (startElement == QLatin1String(aliasTagC))
@@ -242,6 +246,9 @@ bool QMimeTypeParserBase::parse(QIODevice *dev, const QString &fileName, QString
data.addGlobPattern(pattern); // just for QMimeType::globPatterns()
}
break;
+ case ParseGlobDeleteAll:
+ data.globPatterns.clear();
+ break;
case ParseSubClass: {
const QString inheritsFrom = atts.value(QLatin1String(mimeTypeAttributeC)).toString();
if (!inheritsFrom.isEmpty())
diff --git a/src/corelib/mimetypes/qmimetypeparser_p.h b/src/corelib/mimetypes/qmimetypeparser_p.h
index 6f1869e399..9634718ef1 100644
--- a/src/corelib/mimetypes/qmimetypeparser_p.h
+++ b/src/corelib/mimetypes/qmimetypeparser_p.h
@@ -90,6 +90,7 @@ private:
ParseGenericIcon,
ParseIcon,
ParseGlobPattern,
+ ParseGlobDeleteAll,
ParseSubClass,
ParseAlias,
ParseMagic,