Skip to content

Commit abdfcb7

Browse files
committedAug 25, 2021
Support retrieving sublayer path for OGR layers on GDAL 3.4+
1 parent ec80d5a commit abdfcb7

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

59 files changed

+68
-0
lines changed
 

‎src/core/providers/ogr/qgsogrprovidermetadata.cpp

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ email : nyall dot dawson at gmail dot com
3131
#include "qgsproviderutils.h"
3232
#include "qgsgdalutils.h"
3333

34+
#include <gdal.h>
3435
#include <QFileInfo>
3536
#include <QFile>
3637
#include <QDir>
@@ -1305,6 +1306,54 @@ QList<QgsProviderSublayerDetails> QgsOgrProviderMetadata::querySublayers( const
13051306
} ), res.end() );
13061307
}
13071308

1309+
#if GDAL_VERSION_NUM >= GDAL_COMPUTE_VERSION(3,4,0)
1310+
1311+
#if QT_VERSION < QT_VERSION_CHECK(5, 14, 0)
1312+
QMutex *mutex = nullptr;
1313+
#else
1314+
QRecursiveMutex *mutex = nullptr;
1315+
#endif
1316+
GDALDatasetH hDS = firstLayer->getDatasetHandleAndMutex( mutex );
1317+
QMutexLocker locker( mutex );
1318+
if ( GDALGroupH rootGroup = GDALDatasetGetRootGroup( hDS ) )
1319+
{
1320+
std::function< void( GDALGroupH, const QStringList & ) > recurseGroup;
1321+
recurseGroup = [&recurseGroup, &res]( GDALGroupH group, const QStringList & currentPath )
1322+
{
1323+
if ( char **vectorLayerNames = GDALGroupGetVectorLayerNames( group, nullptr ) )
1324+
{
1325+
const QStringList layers = QgsOgrUtils::cStringListToQStringList( vectorLayerNames );
1326+
// attach path to matching layers
1327+
for ( const QString &layer : layers )
1328+
{
1329+
for ( int i = 0; i < res.size(); ++i )
1330+
{
1331+
if ( res.at( i ).name() == layer )
1332+
{
1333+
res[i].setPath( currentPath );
1334+
}
1335+
}
1336+
}
1337+
}
1338+
1339+
if ( char **subgroupNames = GDALGroupGetGroupNames( group, nullptr ) )
1340+
{
1341+
for ( int i = 0; subgroupNames[i]; ++i )
1342+
{
1343+
if ( GDALGroupH subgroup = GDALGroupOpenGroup( group, subgroupNames[i], nullptr ) )
1344+
{
1345+
recurseGroup( subgroup, QStringList( currentPath ) << QString::fromUtf8( subgroupNames[i] ) );
1346+
GDALGroupRelease( subgroup );
1347+
}
1348+
}
1349+
}
1350+
};
1351+
1352+
recurseGroup( rootGroup, {} );
1353+
GDALGroupRelease( rootGroup );
1354+
}
1355+
#endif
1356+
13081357
return res;
13091358
}
13101359

‎tests/src/python/test_provider_ogr.py

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2045,6 +2045,24 @@ def test_provider_sublayer_details(self):
20452045
'driverName': 'SQLite',
20462046
'geomColName': ''}])
20472047

2048+
@unittest.skipIf(int(gdal.VersionInfo('VERSION_NUM')) < GDAL_COMPUTE_VERSION(3, 4, 0), "GDAL 3.4 required")
2049+
def test_provider_sublayer_details_hierarchy(self):
2050+
"""
2051+
Test retrieving sublayer details from a datasource with a hierarchy of layers
2052+
"""
2053+
metadata = QgsProviderRegistry.instance().providerMetadata('ogr')
2054+
2055+
res = metadata.querySublayers(os.path.join(TEST_DATA_DIR, 'featuredataset.gdb'))
2056+
self.assertEqual(len(res), 4)
2057+
self.assertEqual(res[0].name(), 'fd1_lyr1')
2058+
self.assertEqual(res[0].path(), ['fd1'])
2059+
self.assertEqual(res[1].name(), 'fd1_lyr2')
2060+
self.assertEqual(res[1].path(), ['fd1'])
2061+
self.assertEqual(res[2].name(), 'standalone')
2062+
self.assertEqual(res[2].path(), [])
2063+
self.assertEqual(res[3].name(), 'fd2_lyr')
2064+
self.assertEqual(res[3].path(), ['fd2'])
2065+
20482066
def test_provider_sublayer_details_fast_scan(self):
20492067
"""
20502068
Test retrieving sublayer details from data provider metadata, using fast scan

0 commit comments

Comments
 (0)
Please sign in to comment.