Skip to content
Permalink
Browse files

Add QgsDataProvider::ReadFlag::SkipFeatureCount and implement it in O…

…GR provider to avoid featureCount() to be called
  • Loading branch information
rouault committed Nov 12, 2020
1 parent c8510b1 commit 32608075e583254877e7e20a3b70ed819cd2119d
@@ -73,6 +73,7 @@ Abstract base class for spatial data provider implementations.
enum ReadFlag
{
FlagTrustDataSource,
SkipFeatureCount,
};
typedef QFlags<QgsDataProvider::ReadFlag> ReadFlags;

@@ -953,7 +953,8 @@ void QgsOgrProvider::addSubLayerDetailsToSubLayerList( int i, QgsOgrLayer *layer

QStringList QgsOgrProvider::subLayers() const
{
return _subLayers( true );
const bool withFeatureCount = ( mReadFlags & QgsDataProvider::SkipFeatureCount ) == 0;
return _subLayers( withFeatureCount );
}

QgsLayerMetadata QgsOgrProvider::layerMetadata() const
@@ -1604,6 +1605,10 @@ QgsWkbTypes::Type QgsOgrProvider::wkbType() const
*/
long QgsOgrProvider::featureCount() const
{
if ( ( mReadFlags & QgsDataProvider::SkipFeatureCount ) != 0 )
{
return QgsVectorDataProvider::UnknownCount;
}
if ( mRefreshFeatureCount )
{
mRefreshFeatureCount = false;
@@ -122,6 +122,7 @@ class CORE_EXPORT QgsDataProvider : public QObject
enum ReadFlag
{
FlagTrustDataSource = 1 << 0, //!< Trust datasource config (primary key unicity, geometry type and srid, etc). Improves provider load time by skipping expensive checks like primary key unicity, geometry type and srid and by using estimated metadata on data load. Since QGIS 3.16
SkipFeatureCount = 1 << 1, //!< Make featureCount() return -1 to indicate unknown, and subLayers() to return a unknown feature count as well. Since QGIS 3.18. Only implemented by OGR provider at time of writing.
};
Q_DECLARE_FLAGS( ReadFlags, ReadFlag )

@@ -22,12 +22,14 @@
from osgeo import gdal
from qgis.core import (
QgsApplication,
QgsDataProvider,
QgsSettings,
QgsFeature,
QgsField,
QgsGeometry,
QgsVectorLayer,
QgsFeatureRequest,
QgsProviderRegistry,
QgsVectorDataProvider,
QgsWkbTypes,
QgsVectorLayerExporter,
@@ -1076,6 +1078,24 @@ def testEncoding(self):
self.assertTrue(vl.isValid())
self.assertEqual([f.attributes() for f in vl.dataProvider().getFeatures()], [['abcŐ'], ['abcŐabcŐabcŐ']])

def testSkipFeatureCountOnFeatureCount(self):
"""Test QgsDataProvider.SkipFeatureCount on featureCount()"""

testPath = TEST_DATA_DIR + '/' + 'lines.shp'
provider = QgsProviderRegistry.instance().createProvider('ogr', testPath, QgsDataProvider.ProviderOptions(), QgsDataProvider.SkipFeatureCount)
self.assertTrue(provider.isValid())
self.assertEqual(provider.featureCount(), QgsVectorDataProvider.UnknownCount)

def testSkipFeatureCountOnSubLayers(self):
"""Test QgsDataProvider.SkipFeatureCount on subLayers()"""

datasource = os.path.join(TEST_DATA_DIR, 'shapefile')
provider = QgsProviderRegistry.instance().createProvider('ogr', datasource, QgsDataProvider.ProviderOptions(), QgsDataProvider.SkipFeatureCount)
self.assertTrue(provider.isValid())
sublayers = provider.subLayers()
self.assertTrue(len(sublayers) > 1)
self.assertEqual(sublayers[0].split(QgsDataProvider.sublayerSeparator())[2], '-1')


if __name__ == '__main__':
unittest.main()

0 comments on commit 3260807

Please sign in to comment.
You can’t perform that action at this time.