mirror of
https://github.com/qgis/QGIS.git
synced 2025-02-27 00:33:48 -05:00
Fix processing algorithm checkvalidity reason
Fixex #19617 - Check validity algorithm returns empty reason in attribute table
This commit is contained in:
parent
5b7e60ac45
commit
001a81bc46
@ -157,9 +157,6 @@ class CheckValidity(QgisAlgorithm):
|
||||
if not geom.isNull() and not geom.isEmpty():
|
||||
errors = list(geom.validateGeometry(method))
|
||||
if errors:
|
||||
# QGIS method return a summary at the end
|
||||
if method == 1:
|
||||
errors.pop()
|
||||
valid = False
|
||||
reasons = []
|
||||
for error in errors:
|
||||
|
@ -143,6 +143,7 @@ ADD_PYTHON_TEST(PyQgsPointDisplacementRenderer test_qgspointdisplacementrenderer
|
||||
ADD_PYTHON_TEST(PyQgsPostgresDomain test_qgspostgresdomain.py)
|
||||
ADD_PYTHON_TEST(PyQgsProcessingRecentAlgorithmLog test_qgsprocessingrecentalgorithmslog.py)
|
||||
ADD_PYTHON_TEST(PyQgsProcessingInPlace test_qgsprocessinginplace.py)
|
||||
ADD_PYTHON_TEST(PyQgsProcessingCheckValidity test_qgsprocessing_checkvalidity.py)
|
||||
ADD_PYTHON_TEST(PyQgsProjectionSelectionWidgets test_qgsprojectionselectionwidgets.py)
|
||||
ADD_PYTHON_TEST(PyQgsProjectMetadata test_qgsprojectmetadata.py)
|
||||
ADD_PYTHON_TEST(PyQgsRange test_qgsrange.py)
|
||||
|
135
tests/src/python/test_qgsprocessing_checkvalidity.py
Normal file
135
tests/src/python/test_qgsprocessing_checkvalidity.py
Normal file
@ -0,0 +1,135 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
"""QGIS Unit tests for Processing CheckValidity algorithm.
|
||||
|
||||
.. note:: This program is free software; you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation; either version 2 of the License, or
|
||||
(at your option) any later version.
|
||||
"""
|
||||
__author__ = 'Alessandro Pasotti'
|
||||
__date__ = '2018-09'
|
||||
__copyright__ = 'Copyright 2018, The QGIS Project'
|
||||
# This will get replaced with a git SHA1 when you do a git archive
|
||||
__revision__ = '$Format:%H$'
|
||||
|
||||
from qgis.PyQt.QtCore import QCoreApplication, QVariant
|
||||
from qgis.core import (
|
||||
QgsFeature,
|
||||
QgsGeometry,
|
||||
QgsApplication,
|
||||
QgsMemoryProviderUtils,
|
||||
QgsWkbTypes,
|
||||
QgsField,
|
||||
QgsFields,
|
||||
QgsProcessingContext,
|
||||
QgsProcessingFeedback,
|
||||
QgsCoordinateReferenceSystem,
|
||||
QgsProject,
|
||||
QgsProcessingException,
|
||||
QgsProcessingUtils,
|
||||
QgsSettings
|
||||
)
|
||||
from processing.core.Processing import Processing
|
||||
from processing.gui.AlgorithmExecutor import execute
|
||||
from qgis.testing import start_app, unittest
|
||||
from qgis.PyQt.QtTest import QSignalSpy
|
||||
from qgis.analysis import QgsNativeAlgorithms
|
||||
|
||||
start_app()
|
||||
|
||||
|
||||
class ConsoleFeedBack(QgsProcessingFeedback):
|
||||
|
||||
def reportError(self, error, fatalError=False):
|
||||
print(error)
|
||||
|
||||
|
||||
class TestQgsProcessingCheckValidity(unittest.TestCase):
|
||||
|
||||
@classmethod
|
||||
def setUpClass(cls):
|
||||
"""Run before all tests"""
|
||||
QCoreApplication.setOrganizationName("QGIS_Test")
|
||||
QCoreApplication.setOrganizationDomain(
|
||||
"QGIS_TestPyQgsProcessingCheckValidity.com")
|
||||
QCoreApplication.setApplicationName(
|
||||
"QGIS_TestPyQgsProcessingCheckValidity")
|
||||
QgsSettings().clear()
|
||||
Processing.initialize()
|
||||
QgsApplication.processingRegistry().addProvider(QgsNativeAlgorithms())
|
||||
cls.registry = QgsApplication.instance().processingRegistry()
|
||||
|
||||
def _make_layer(self, layer_wkb_name):
|
||||
fields = QgsFields()
|
||||
wkb_type = getattr(QgsWkbTypes, layer_wkb_name)
|
||||
fields.append(QgsField('int_f', QVariant.Int))
|
||||
layer = QgsMemoryProviderUtils.createMemoryLayer(
|
||||
'%s_layer' % layer_wkb_name, fields, wkb_type, QgsCoordinateReferenceSystem(4326))
|
||||
self.assertTrue(layer.isValid())
|
||||
self.assertEqual(layer.wkbType(), wkb_type)
|
||||
return layer
|
||||
|
||||
def test_check_validity(self):
|
||||
"""Test that the output invalid contains the error reason"""
|
||||
|
||||
polygon_layer = self._make_layer('Polygon')
|
||||
self.assertTrue(polygon_layer.startEditing())
|
||||
f = QgsFeature(polygon_layer.fields())
|
||||
f.setAttributes([1])
|
||||
# Flake!
|
||||
f.setGeometry(QgsGeometry.fromWkt(
|
||||
'POLYGON ((0 0, 2 2, 0 2, 2 0, 0 0))'))
|
||||
self.assertTrue(f.isValid())
|
||||
f2 = QgsFeature(polygon_layer.fields())
|
||||
f2.setAttributes([1])
|
||||
f2.setGeometry(QgsGeometry.fromWkt(
|
||||
'POLYGON((1.1 1.1, 1.1 2.1, 2.1 2.1, 2.1 1.1, 1.1 1.1))'))
|
||||
self.assertTrue(f2.isValid())
|
||||
self.assertTrue(polygon_layer.addFeatures([f, f2]))
|
||||
polygon_layer.commitChanges()
|
||||
polygon_layer.rollBack()
|
||||
self.assertEqual(polygon_layer.featureCount(), 2)
|
||||
|
||||
QgsProject.instance().addMapLayers([polygon_layer])
|
||||
|
||||
alg = self.registry.createAlgorithmById('qgis:checkvalidity')
|
||||
|
||||
context = QgsProcessingContext()
|
||||
context.setProject(QgsProject.instance())
|
||||
feedback = ConsoleFeedBack()
|
||||
|
||||
self.assertIsNotNone(alg)
|
||||
parameters = {}
|
||||
parameters['INPUT_LAYER'] = polygon_layer.id()
|
||||
parameters['VALID_OUTPUT'] = 'memory:'
|
||||
parameters['INVALID_OUTPUT'] = 'memory:'
|
||||
parameters['ERROR_OUTPUT'] = 'memory:'
|
||||
|
||||
# QGIS method
|
||||
parameters['METHOD'] = 1
|
||||
ok, results = execute(
|
||||
alg, parameters, context=context, feedback=feedback)
|
||||
self.assertTrue(ok)
|
||||
invalid_layer = QgsProcessingUtils.mapLayerFromString(
|
||||
results['INVALID_OUTPUT'], context)
|
||||
self.assertEqual(invalid_layer.fields().names()[-1], '_errors')
|
||||
self.assertEqual(invalid_layer.featureCount(), 1)
|
||||
f = next(invalid_layer.getFeatures())
|
||||
self.assertEqual(f.attributes(), [
|
||||
1, 'segments 0 and 2 of line 0 intersect at 1, 1\nGeometry has 1 errors.'])
|
||||
|
||||
# GEOS method
|
||||
parameters['METHOD'] = 2
|
||||
ok, results = execute(
|
||||
alg, parameters, context=context, feedback=feedback)
|
||||
self.assertTrue(ok)
|
||||
invalid_layer = QgsProcessingUtils.mapLayerFromString(
|
||||
results['INVALID_OUTPUT'], context)
|
||||
self.assertEqual(invalid_layer.fields().names()[-1], '_errors')
|
||||
self.assertEqual(invalid_layer.featureCount(), 1)
|
||||
f = next(invalid_layer.getFeatures())
|
||||
self.assertEqual(f.attributes(), [1, 'Self-intersection'])
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
unittest.main()
|
Loading…
x
Reference in New Issue
Block a user