Skip to content
Permalink
Browse files

[Bugfix][Server] QGIS Server removes empty string in style parameter …

…even if it describes default style

In OGC WMS standard, the empty string represents the default style.

QGIS Server when it parses the parameters, QGIS Server when it parses parameters it removes empty parts.
When all requested styles are default ones it's equal to an empty parameter STYLE, as defined in the standard.
When only one layer is requested, there is no issue with custom or default style.
When multiple layers are requested and some with custom styles, because QGIS Server does not retain empty strings, it loses the layer / style match.

To fix it, keeps empty parts for not empty styles parameters.
  • Loading branch information
rldhont committed Apr 5, 2019
1 parent 76efbc6 commit d6864b9a0047ed58cffc2c30565b800177f95689
@@ -48,11 +48,12 @@ Returns true if the parameter is valid, false otherwise.
Converts the parameter into a string.
%End

QStringList toStringList( char delimiter = ',' ) const;
QStringList toStringList( char delimiter = ',', bool skipEmptyParts = true ) const;
%Docstring
Converts the parameter into a list of strings.
Converts the parameter into a list of strings

:param delimiter: The character used for delimiting
:param skipEmptyParts: To use QString.SkipEmptyParts for splitting

:return: A list of strings
%End
@@ -67,9 +67,21 @@ QString QgsServerParameterDefinition::toString() const
return mValue.toString();
}

QStringList QgsServerParameterDefinition::toStringList( const char delimiter ) const
QStringList QgsServerParameterDefinition::toStringList( const char delimiter, const bool skipEmptyParts ) const
{
return toString().split( delimiter, QString::SkipEmptyParts );
if ( skipEmptyParts )
{
return toString().split( delimiter, QString::SkipEmptyParts );
}
else
{
QStringList list;
if ( !toString().isEmpty() )
{
list = toString().split( delimiter, QString::KeepEmptyParts );
}
return list;
}
}

QList<QgsGeometry> QgsServerParameterDefinition::toGeomList( bool &ok, const char delimiter ) const
@@ -64,11 +64,12 @@ class SERVER_EXPORT QgsServerParameterDefinition
QString toString() const;

/**
* Converts the parameter into a list of strings.
* Converts the parameter into a list of strings
* \param delimiter The character used for delimiting
* \param skipEmptyParts To use QString::SkipEmptyParts for splitting
* \returns A list of strings
*/
QStringList toStringList( char delimiter = ',' ) const;
QStringList toStringList( char delimiter = ',', bool skipEmptyParts = true ) const;

/**
* Converts the parameter into a list of integers.
@@ -43,6 +43,11 @@ namespace QgsWms
QgsServerParameterDefinition::raiseError( msg );
}

QStringList QgsWmsParameter::toStyleList( const char delimiter ) const
{
return QgsServerParameterDefinition::toStringList( delimiter, false );
}

QList<QgsGeometry> QgsWmsParameter::toGeomList( const char delimiter ) const
{
bool ok = true;
@@ -1298,8 +1303,8 @@ namespace QgsWms

QStringList QgsWmsParameters::allStyles() const
{
QStringList style = mWmsParameters[ QgsWmsParameter::STYLE ].toStringList();
const QStringList styles = mWmsParameters[ QgsWmsParameter::STYLES ].toStringList();
QStringList style = mWmsParameters[ QgsWmsParameter::STYLE ].toStyleList();
const QStringList styles = mWmsParameters[ QgsWmsParameter::STYLES ].toStyleList();
return style << styles;
}

@@ -1561,7 +1566,7 @@ namespace QgsWms
wmsParam = idParameter( QgsWmsParameter::STYLES, mapId );
if ( wmsParam.isValid() )
{
styles = wmsParam.toStringList();
styles = wmsParam.toStyleList();
}

QList<QgsWmsParametersLayer> lParams;
@@ -191,6 +191,15 @@ namespace QgsWms
*/
bool isValid() const override;

/**
* Converts the parameter into a list of strings and keeps empty parts
* Default style value is an empty string
* \param delimiter The character used for delimiting
* \returns A list of strings
* \since QGIS 3.8
*/
QStringList toStyleList( const char delimiter = ',' ) const;

/**
* Converts the parameter into a list of geometries.
* \param delimiter The character delimiting string geometries
@@ -723,6 +723,58 @@ def test_wms_getmap_style(self):
r, h = self._result(self._execute_request(qs))
self._img_diff_error(r, h, "WMS_GetMap_StyleCustom")

# mixed custom and default style with STYLES parameter
qs = "?" + "&".join(["%s=%s" % i for i in list({
"MAP": urllib.parse.quote(self.projectPath),
"SERVICE": "WMS",
"VERSION": "1.1.1",
"REQUEST": "GetMap",
"LAYERS": "Country_Labels,Hello",
"STYLES": "custom,",
"FORMAT": "image/png",
"BBOX": "-16817707,-4710778,5696513,14587125",
"HEIGHT": "500",
"WIDTH": "500",
"CRS": "EPSG:3857"
}.items())])

r, h = self._result(self._execute_request(qs))
self._img_diff_error(r, h, "WMS_GetMap_StyleMixed")

qs = "?" + "&".join(["%s=%s" % i for i in list({
"MAP": urllib.parse.quote(self.projectPath),
"SERVICE": "WMS",
"VERSION": "1.1.1",
"REQUEST": "GetMap",
"LAYERS": "Hello,Country_Labels",
"STYLES": "default,custom",
"FORMAT": "image/png",
"BBOX": "-16817707,-4710778,5696513,14587125",
"HEIGHT": "500",
"WIDTH": "500",
"CRS": "EPSG:3857"
}.items())])

r, h = self._result(self._execute_request(qs))
self._img_diff_error(r, h, "WMS_GetMap_StyleMixed_LayerOrder")

qs = "?" + "&".join(["%s=%s" % i for i in list({
"MAP": urllib.parse.quote(self.projectPath),
"SERVICE": "WMS",
"VERSION": "1.1.1",
"REQUEST": "GetMap",
"LAYERS": "Hello,Country_Labels",
"STYLES": ",custom",
"FORMAT": "image/png",
"BBOX": "-16817707,-4710778,5696513,14587125",
"HEIGHT": "500",
"WIDTH": "500",
"CRS": "EPSG:3857"
}.items())])

r, h = self._result(self._execute_request(qs))
self._img_diff_error(r, h, "WMS_GetMap_StyleMixed_LayerOrder")

def test_wms_getmap_filter(self):
qs = "?" + "&".join(["%s=%s" % i for i in list({
"MAP": urllib.parse.quote(self.projectPath),
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.

0 comments on commit d6864b9

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