Skip to content
Permalink
Browse files

Fix OGR expression compiler with GDAL >= 2.0

Some extreme corner cases (eg "NULL OR TRUE") tested by the provider
tests were failing with GDAL 2.0. In GDAL<2.0 these expressions would
be rejected by OGR, but it seems GDAL>=2.0 has partial support for
these so the expression compiler needs to handle them before handing
off to GDAL.
  • Loading branch information
nyalldawson committed Mar 3, 2016
1 parent 4dbd884 commit 81be55937538307efed3b76b518fba4fa699545e
@@ -162,10 +162,22 @@ QgsSqlExpressionCompiler::Result QgsSqlExpressionCompiler::compileNode( const Qg
break;

case QgsExpression::boOr:
if ( mFlags.testFlag( NoNullInBooleanLogic ) )
{
if ( nodeIsNullLiteral( n->opLeft() ) || nodeIsNullLiteral( n->opRight() ) )
return Fail;
}

op = "OR";
break;

case QgsExpression::boAnd:
if ( mFlags.testFlag( NoNullInBooleanLogic ) )
{
if ( nodeIsNullLiteral( n->opLeft() ) || nodeIsNullLiteral( n->opRight() ) )
return Fail;
}

op = "AND";
break;

@@ -297,3 +309,12 @@ QgsSqlExpressionCompiler::Result QgsSqlExpressionCompiler::compileNode( const Qg

return Fail;
}

bool QgsSqlExpressionCompiler::nodeIsNullLiteral( const QgsExpression::Node* node ) const
{
if ( node->nodeType() != QgsExpression::ntLiteral )
return false;

const QgsExpression::NodeLiteral* nLit = static_cast<const QgsExpression::NodeLiteral*>( node );
return nLit->value().isNull();
}
@@ -49,6 +49,7 @@ class CORE_EXPORT QgsSqlExpressionCompiler
{
CaseInsensitiveStringMatch = 0x01, //!< Provider performs case-insensitive string matching for all strings
LikeIsCaseInsensitive = 0x02, //!< Provider treats LIKE as case-insensitive
NoNullInBooleanLogic = 0x04, //!< Provider does not support using NULL with boolean logic, eg "(...) OR NULL"
};
Q_DECLARE_FLAGS( Flags, Flag )

@@ -98,6 +99,8 @@ class CORE_EXPORT QgsSqlExpressionCompiler

Flags mFlags;

bool nodeIsNullLiteral( const QgsExpression::Node* node ) const;

};

Q_DECLARE_OPERATORS_FOR_FLAGS( QgsSqlExpressionCompiler::Flags )
@@ -17,7 +17,7 @@
#include "qgsogrprovider.h"

QgsOgrExpressionCompiler::QgsOgrExpressionCompiler( QgsOgrFeatureSource* source )
: QgsSqlExpressionCompiler( source->mFields, QgsSqlExpressionCompiler::CaseInsensitiveStringMatch )
: QgsSqlExpressionCompiler( source->mFields, QgsSqlExpressionCompiler::CaseInsensitiveStringMatch | QgsSqlExpressionCompiler::NoNullInBooleanLogic )
, mSource( source )
{
}
@@ -95,5 +95,12 @@ QString QgsOgrExpressionCompiler::quotedIdentifier( const QString& identifier )
QString QgsOgrExpressionCompiler::quotedValue( const QVariant& value, bool& ok )
{
ok = true;

if ( value.type() == QVariant::Bool )
{
// No support for boolean literals, so fake them
return value.toBool() ? "(1=1)" : "(1=0)";
}

return QgsOgrProviderUtils::quotedValue( value );
}

0 comments on commit 81be559

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