Skip to content

Commit

Permalink
Server WFS: handle axis order in BBOX
Browse files Browse the repository at this point in the history
Follows GeoServer convention, fixes #36584
  • Loading branch information
elpaso committed Jan 29, 2021
1 parent 84f61ff commit e967fd9
Show file tree
Hide file tree
Showing 2 changed files with 31 additions and 2 deletions.
16 changes: 15 additions & 1 deletion src/server/services/wfs/qgswfsgetfeature.cpp
Expand Up @@ -544,7 +544,7 @@ namespace QgsWfs
}

// each Feature requested by FEATUREID can have each own property list
QString key = QStringLiteral( "%1(%2)" ).arg( typeName ).arg( propertyName );
QString key = QStringLiteral( "%1(%2)" ).arg( typeName, propertyName );
QStringList fids;
if ( fidsMap.contains( key ) )
{
Expand Down Expand Up @@ -734,12 +734,15 @@ namespace QgsWfs
// get bbox extent
QgsRectangle extent = mWfsParameters.bboxAsRectangle();

QString extentSrsName { mWfsParameters.srsName() };

// handle WFS 1.1.0 optional CRS
if ( mWfsParameters.bbox().split( ',' ).size() == 5 && ! mWfsParameters.srsName().isEmpty() )
{
QString crs( mWfsParameters.bbox().split( ',' )[4] );
if ( crs != mWfsParameters.srsName() )
{
extentSrsName = crs;
QgsCoordinateReferenceSystem sourceCrs( crs );
QgsCoordinateReferenceSystem destinationCrs( mWfsParameters.srsName() );
if ( sourceCrs.isValid() && destinationCrs.isValid( ) )
Expand All @@ -763,6 +766,17 @@ namespace QgsWfs
}
}

// Follow GeoServer conventions and handle axis order
// See: https://docs.geoserver.org/latest/en/user/services/wfs/axis_order.html#wfs-basics-axis
QgsCoordinateReferenceSystem extentCrs;
extentCrs.createFromUserInput( extentSrsName );
if ( extentCrs.isValid() && extentCrs.hasAxisInverted() && ! extentSrsName.startsWith( QStringLiteral( "EPSG:" ) ) )
{
QgsGeometry geom { QgsGeometry::fromRect( extent ) };
geom.get()->swapXy();
extent = geom.boundingBox();
}

// set feature request filter rectangle
QList<getFeatureQuery>::iterator qIt = request.queries.begin();
for ( ; qIt != request.queries.end(); ++qIt )
Expand Down
17 changes: 16 additions & 1 deletion tests/src/python/test_qgsserver_wfs.py
Expand Up @@ -724,7 +724,7 @@ def _test(version, srsName, lat_lon=False):
query_string, requestMethod=QgsServerRequest.PostMethod, data=request.encode('utf-8'))
feature = next(vl.getFeatures(QgsFeatureRequest(QgsExpression('"name" = \'%s\'' % name))))
geom = feature.geometry()
self.assertEqual(geom.asWkt(0), geom_4326.asWkt(0), "Failed: %s , %s, lat_lon=%s" % (version, srsName, lat_lon))
self.assertEqual(geom.asWkt(0), geom_4326.asWkt(0), "Transaction Failed: %s , %s, lat_lon=%s" % (version, srsName, lat_lon))

_test('1.1.0', 'urn:ogc:def:crs:EPSG::4326', lat_lon=True)
_test('1.1.0', 'http://www.opengis.net/def/crs/EPSG/0/4326', lat_lon=True)
Expand All @@ -736,6 +736,21 @@ def _test(version, srsName, lat_lon=False):
_test('1.0.0', 'http://www.opengis.net/gml/srs/epsg.xml#4326', lat_lon=False)
_test('1.0.0', 'EPSG:4326', lat_lon=False)

def _test_getFeature(version, srsName, lat_lon=False):
# Now get the feature through WFS using BBOX filter
bbox = QgsGeometry.fromWkt('point( 10.7006 52.4317)').boundingBox()
bbox.grow(0.0001)
bbox_text = "%s,%s,%s,%s" % ((bbox.yMinimum(), bbox.xMinimum(), bbox.yMaximum(), bbox.xMaximum()) if lat_lon else (bbox.xMinimum(), bbox.yMinimum(), bbox.xMaximum(), bbox.yMaximum()))
req = query_string + '&REQUEST=GetFeature&VERSION={version}&TYPENAME=as_symbols&SRSNAME={srsName}&BBOX={bbox},{srsName}'.format(version=version, srsName=srsName, bbox=bbox_text)
header, body = self._execute_request(req)
self.assertTrue(b'gid>7' in body, "GetFeature Failed: %s , %s, lat_lon=%s" % (version, srsName, lat_lon))

_test_getFeature('1.1.0', 'urn:ogc:def:crs:EPSG::4326', lat_lon=True)
_test_getFeature('1.1.0', 'EPSG:4326', lat_lon=False)

_test_getFeature('1.0.0', 'urn:ogc:def:crs:EPSG::4326', lat_lon=True)
_test_getFeature('1.0.0', 'EPSG:4326', lat_lon=False)

# Cleanup
self.assertTrue(vl.startEditing())
vl.selectByExpression('"name" LIKE \'4326-test%\'')
Expand Down

0 comments on commit e967fd9

Please sign in to comment.