26#include <QRegularExpression>
28const char *QgsExpressionNodeBinaryOperator::BINARY_OPERATOR_TEXT[] =
32 "=",
"<>",
"<=",
">=",
"<",
">",
"~",
"LIKE",
"NOT LIKE",
"ILIKE",
"NOT ILIKE",
"IS",
"IS NOT",
33 "+",
"-",
"*",
"/",
"//",
"%",
"^",
37const char *QgsExpressionNodeUnaryOperator::UNARY_OPERATOR_TEXT[] =
46 const QList< QgsExpressionNode * > nodeList = mList->
list();
48 needs |= n->needsGeometry();
59 mList.append( node->
node );
60 mNameList.append( cleanNamedNodeName( node->
name ) );
61 mHasNamedNodes =
true;
70 nl->mList.append( node->clone() );
72 nl->mNameList = mNameList;
83 if ( !first ) msg += QLatin1String(
", " );
90QString QgsExpressionNode::NodeList::cleanNamedNodeName(
const QString &name )
92 QString cleaned = name.toLower();
95 if ( cleaned == QLatin1String(
"geom" ) )
96 cleaned = QStringLiteral(
"geometry" );
97 else if ( cleaned == QLatin1String(
"val" ) )
98 cleaned = QStringLiteral(
"value" );
99 else if ( cleaned == QLatin1String(
"geometry a" ) )
100 cleaned = QStringLiteral(
"geometry1" );
101 else if ( cleaned == QLatin1String(
"geometry b" ) )
102 cleaned = QStringLiteral(
"geometry2" );
103 else if ( cleaned == QLatin1String(
"i" ) )
104 cleaned = QStringLiteral(
"vertex" );
114 QVariant val = mOperand->eval( parent, context );
121 QgsExpressionUtils::TVL tvl = QgsExpressionUtils::getTVLValue( val, parent );
123 return QgsExpressionUtils::tvl2variant( QgsExpressionUtils::NOT[tvl] );
127 if ( QgsExpressionUtils::isIntSafe( val ) )
128 return QVariant( - QgsExpressionUtils::getIntValue( val, parent ) );
129 else if ( QgsExpressionUtils::isDoubleSafe( val ) )
130 return QVariant( - QgsExpressionUtils::getDoubleValue( val, parent ) );
144 return mOperand->prepare( parent, context );
150 return QStringLiteral(
"%1 ( %2 )" ).arg( UNARY_OPERATOR_TEXT[mOp], mOperand->dump() );
152 return QStringLiteral(
"%1 %2" ).arg( UNARY_OPERATOR_TEXT[mOp], mOperand->dump() );
158 return QSet< QString >();
160 return mOperand->referencedColumns();
165 return mOperand->referencedVariables();
170 return mOperand->referencedFunctions();
175 QList<const QgsExpressionNode *> lst;
177 lst += mOperand->nodes();
183 return mOperand->needsGeometry();
195 return mOperand->
isStatic( parent, context );
200 return UNARY_OPERATOR_TEXT[mOp];
207 QVariant vL = mOpLeft->eval( parent, context );
210 if ( mOp == boAnd || mOp == boOr )
212 QgsExpressionUtils::TVL tvlL = QgsExpressionUtils::getTVLValue( vL, parent );
214 if ( mOp == boAnd && tvlL == QgsExpressionUtils::False )
216 if ( mOp == boOr && tvlL == QgsExpressionUtils::True )
220 QVariant vR = mOpRight->eval( parent, context );
226 if ( vL.type() == QVariant::String && vR.type() == QVariant::String )
228 QString sL = QgsExpressionUtils::isNull( vL ) ? QString() : QgsExpressionUtils::getStringValue( vL, parent );
230 QString sR = QgsExpressionUtils::isNull( vR ) ? QString() : QgsExpressionUtils::getStringValue( vR, parent );
232 return QVariant( sL + sR );
241 if ( QgsExpressionUtils::isNull( vL ) || QgsExpressionUtils::isNull( vR ) )
243 else if ( mOp != boDiv && QgsExpressionUtils::isIntSafe( vL ) && QgsExpressionUtils::isIntSafe( vR ) )
246 qlonglong iL = QgsExpressionUtils::getIntValue( vL, parent );
248 qlonglong iR = QgsExpressionUtils::getIntValue( vR, parent );
251 if ( mOp == boMod && iR == 0 )
254 return QVariant( computeInt( iL, iR ) );
256 else if ( QgsExpressionUtils::isDateTimeSafe( vL ) && QgsExpressionUtils::isIntervalSafe( vR ) )
258 QDateTime dL = QgsExpressionUtils::getDateTimeValue( vL, parent );
260 QgsInterval iL = QgsExpressionUtils::getInterval( vR, parent );
262 if ( mOp == boDiv || mOp == boMul || mOp == boMod )
264 parent->
setEvalErrorString( tr(
"Can't perform /, *, or % on DateTime and Interval" ) );
267 return QVariant( computeDateTimeFromInterval( dL, &iL ) );
269 else if ( mOp == boPlus && ( ( vL.type() == QVariant::Date && vR.type() == QVariant::Time ) ||
270 ( vR.type() == QVariant::Date && vL.type() == QVariant::Time ) ) )
272 QDate date = QgsExpressionUtils::getDateValue( vL.type() == QVariant::Date ? vL : vR, parent );
274 QTime time = QgsExpressionUtils::getTimeValue( vR.type() == QVariant::Time ? vR : vL, parent );
276 QDateTime dt = QDateTime( date, time );
277 return QVariant( dt );
279 else if ( mOp == boMinus && vL.type() == QVariant::Date && vR.type() == QVariant::Date )
281 QDate date1 = QgsExpressionUtils::getDateValue( vL, parent );
283 QDate date2 = QgsExpressionUtils::getDateValue( vR, parent );
285 return date1 - date2;
287 else if ( mOp == boMinus && vL.type() == QVariant::Time && vR.type() == QVariant::Time )
289 QTime time1 = QgsExpressionUtils::getTimeValue( vL, parent );
291 QTime time2 = QgsExpressionUtils::getTimeValue( vR, parent );
293 return time1 - time2;
295 else if ( mOp == boMinus && vL.type() == QVariant::DateTime && vR.type() == QVariant::DateTime )
297 QDateTime datetime1 = QgsExpressionUtils::getDateTimeValue( vL, parent );
299 QDateTime datetime2 = QgsExpressionUtils::getDateTimeValue( vR, parent );
306 double fL = QgsExpressionUtils::getDoubleValue( vL, parent );
308 double fR = QgsExpressionUtils::getDoubleValue( vR, parent );
310 if ( ( mOp == boDiv || mOp == boMod ) && fR == 0. )
312 return QVariant( computeDouble( fL, fR ) );
318 double fL = QgsExpressionUtils::getDoubleValue( vL, parent );
320 double fR = QgsExpressionUtils::getDoubleValue( vR, parent );
324 return QVariant( qlonglong( std::floor( fL / fR ) ) );
327 if ( QgsExpressionUtils::isNull( vL ) || QgsExpressionUtils::isNull( vR ) )
331 double fL = QgsExpressionUtils::getDoubleValue( vL, parent );
333 double fR = QgsExpressionUtils::getDoubleValue( vR, parent );
335 return QVariant( std::pow( fL, fR ) );
340 QgsExpressionUtils::TVL tvlL = QgsExpressionUtils::getTVLValue( vL, parent ), tvlR = QgsExpressionUtils::getTVLValue( vR, parent );
342 return QgsExpressionUtils::tvl2variant( QgsExpressionUtils::AND[tvlL][tvlR] );
347 QgsExpressionUtils::TVL tvlL = QgsExpressionUtils::getTVLValue( vL, parent ), tvlR = QgsExpressionUtils::getTVLValue( vR, parent );
349 return QgsExpressionUtils::tvl2variant( QgsExpressionUtils::OR[tvlL][tvlR] );
358 if ( QgsExpressionUtils::isNull( vL ) || QgsExpressionUtils::isNull( vR ) )
362 else if ( QgsExpressionUtils::isList( vL ) || QgsExpressionUtils::isList( vR ) )
365 if ( !QgsExpressionUtils::isList( vL ) || !QgsExpressionUtils::isList( vR ) )
369 QVariantList lL = vL.toList();
370 QVariantList lR = vR.toList();
371 for (
int i = 0; i < lL.length() && i < lR.length(); i++ )
373 if ( QgsExpressionUtils::isNull( lL.at( i ) ) && QgsExpressionUtils::isNull( lR.at( i ) ) )
376 if ( QgsExpressionUtils::isNull( lL.at( i ) ) || QgsExpressionUtils::isNull( lR.at( i ) ) )
386 return QgsExpressionUtils::isNull( lR.at( i ) );
389 return QgsExpressionUtils::isNull( lL.at( i ) );
399 QVariant eq = eqNode.
eval( parent, context );
401 if ( eq == TVL_False )
405 QVariant v = node.
eval( parent, context );
415 return lL.length() == lR.length();
417 return lL.length() != lR.length();
419 return lL.length() < lR.length();
421 return lL.length() > lR.length();
423 return lL.length() <= lR.length();
425 return lL.length() >= lR.length();
431 else if ( ( vL.type() == QVariant::DateTime && vR.type() == QVariant::DateTime ) )
433 QDateTime dL = QgsExpressionUtils::getDateTimeValue( vL, parent );
435 QDateTime dR = QgsExpressionUtils::getDateTimeValue( vR, parent );
442 dL.setTimeSpec( Qt::UTC );
443 dR.setTimeSpec( Qt::UTC );
445 return compare( dR.msecsTo( dL ) ) ? TVL_True : TVL_False;
447 else if ( ( vL.type() == QVariant::Date && vR.type() == QVariant::Date ) )
449 const QDate dL = QgsExpressionUtils::getDateValue( vL, parent );
451 const QDate dR = QgsExpressionUtils::getDateValue( vR, parent );
453 return compare( dR.daysTo( dL ) ) ? TVL_True : TVL_False;
455 else if ( ( vL.type() == QVariant::Time && vR.type() == QVariant::Time ) )
457 const QTime dL = QgsExpressionUtils::getTimeValue( vL, parent );
459 const QTime dR = QgsExpressionUtils::getTimeValue( vR, parent );
461 return compare( dR.msecsTo( dL ) ) ? TVL_True : TVL_False;
463 else if ( ( vL.type() != QVariant::String || vR.type() != QVariant::String ) &&
464 QgsExpressionUtils::isDoubleSafe( vL ) && QgsExpressionUtils::isDoubleSafe( vR ) )
468 double fL = QgsExpressionUtils::getDoubleValue( vL, parent );
470 double fR = QgsExpressionUtils::getDoubleValue( vR, parent );
472 return compare( fL - fR ) ? TVL_True : TVL_False;
475 else if ( vL.userType() == QMetaType::type(
"QgsInterval" ) && vR.userType() == QMetaType::type(
"QgsInterval" ) )
477 double fL = QgsExpressionUtils::getInterval( vL, parent ).seconds();
479 double fR = QgsExpressionUtils::getInterval( vR, parent ).seconds();
481 return compare( fL - fR ) ? TVL_True : TVL_False;
486 QString sL = QgsExpressionUtils::getStringValue( vL, parent );
488 QString sR = QgsExpressionUtils::getStringValue( vR, parent );
490 int diff = QString::compare( sL, sR );
491 return compare( diff ) ? TVL_True : TVL_False;
496 if ( QgsExpressionUtils::isNull( vL ) && QgsExpressionUtils::isNull( vR ) )
497 return ( mOp == boIs ? TVL_True : TVL_False );
498 else if ( QgsExpressionUtils::isNull( vL ) || QgsExpressionUtils::isNull( vR ) )
499 return ( mOp == boIs ? TVL_False : TVL_True );
503 if ( QgsExpressionUtils::isDoubleSafe( vL ) && QgsExpressionUtils::isDoubleSafe( vR ) &&
504 ( vL.type() != QVariant::String || vR.type() != QVariant::String ) )
506 double fL = QgsExpressionUtils::getDoubleValue( vL, parent );
508 double fR = QgsExpressionUtils::getDoubleValue( vR, parent );
514 QString sL = QgsExpressionUtils::getStringValue( vL, parent );
516 QString sR = QgsExpressionUtils::getStringValue( vR, parent );
518 equal = QString::compare( sL, sR ) == 0;
521 return mOp == boIs ? TVL_True : TVL_False;
523 return mOp == boIs ? TVL_False : TVL_True;
531 if ( QgsExpressionUtils::isNull( vL ) || QgsExpressionUtils::isNull( vR ) )
535 QString
str = QgsExpressionUtils::getStringValue( vL, parent );
537 QString regexp = QgsExpressionUtils::getStringValue( vR, parent );
541 if ( mOp == boLike || mOp == boILike || mOp == boNotLike || mOp == boNotILike )
545 if ( esc_regexp.startsWith(
'%' ) )
547 esc_regexp.replace( 0, 1, QStringLiteral(
".*" ) );
549 const thread_local QRegularExpression rx1( QStringLiteral(
"[^\\\\](%)" ) );
551 while ( ( pos = esc_regexp.indexOf( rx1, pos ) ) != -1 )
553 esc_regexp.replace( pos + 1, 1, QStringLiteral(
".*" ) );
556 const thread_local QRegularExpression rx2( QStringLiteral(
"\\\\%" ) );
557 esc_regexp.replace( rx2, QStringLiteral(
"%" ) );
558 if ( esc_regexp.startsWith(
'_' ) )
560 esc_regexp.replace( 0, 1, QStringLiteral(
"." ) );
562 const thread_local QRegularExpression rx3( QStringLiteral(
"[^\\\\](_)" ) );
564 while ( ( pos = esc_regexp.indexOf( rx3, pos ) ) != -1 )
566 esc_regexp.replace( pos + 1, 1,
'.' );
569 esc_regexp.replace( QLatin1String(
"\\\\_" ), QLatin1String(
"_" ) );
571 matches = QRegularExpression( QRegularExpression::anchoredPattern( esc_regexp ), mOp == boLike || mOp == boNotLike ? QRegularExpression::DotMatchesEverythingOption : QRegularExpression::DotMatchesEverythingOption | QRegularExpression::CaseInsensitiveOption ).match(
str ).hasMatch();
575 matches = QRegularExpression( regexp ).match(
str ).hasMatch();
578 if ( mOp == boNotLike || mOp == boNotILike )
583 return matches ? TVL_True : TVL_False;
587 if ( QgsExpressionUtils::isNull( vL ) || QgsExpressionUtils::isNull( vR ) )
591 QString sL = QgsExpressionUtils::getStringValue( vL, parent );
593 QString sR = QgsExpressionUtils::getStringValue( vR, parent );
595 return QVariant( sL + sR );
602bool QgsExpressionNodeBinaryOperator::compare(
double diff )
624qlonglong QgsExpressionNodeBinaryOperator::computeInt( qlonglong x, qlonglong y )
644QDateTime QgsExpressionNodeBinaryOperator::computeDateTimeFromInterval(
const QDateTime &d,
QgsInterval *i )
649 return d.addSecs( i->
seconds() );
651 return d.addSecs( -i->
seconds() );
658double QgsExpressionNodeBinaryOperator::computeDouble(
double x,
double y )
671 return std::fmod( x, y );
685 bool resL = mOpLeft->prepare( parent, context );
686 bool resR = mOpRight->prepare( parent, context );
732 Q_ASSERT(
false &&
"unexpected binary operator" );
768 Q_ASSERT(
false &&
"unexpected binary operator" );
778 QString rdump( mOpRight->dump() );
783 rdump.prepend(
'(' ).append(
')' );
787 if ( leftAssociative() )
789 fmt += lOp && ( lOp->
precedence() < precedence() ) ? QStringLiteral(
"(%1)" ) : QStringLiteral(
"%1" );
790 fmt += QLatin1String(
" %2 " );
791 fmt += rOp && ( rOp->
precedence() <= precedence() ) ? QStringLiteral(
"(%3)" ) : QStringLiteral(
"%3" );
795 fmt += lOp && ( lOp->
precedence() <= precedence() ) ? QStringLiteral(
"(%1)" ) : QStringLiteral(
"%1" );
796 fmt += QLatin1String(
" %2 " );
797 fmt += rOp && ( rOp->
precedence() < precedence() ) ? QStringLiteral(
"(%3)" ) : QStringLiteral(
"%3" );
800 return fmt.arg( mOpLeft->dump(), BINARY_OPERATOR_TEXT[mOp], rdump );
806 return QSet< QString >();
808 return mOpLeft->referencedColumns() + mOpRight->referencedColumns();
813 return mOpLeft->referencedVariables() + mOpRight->referencedVariables();
818 return mOpLeft->referencedFunctions() + mOpRight->referencedFunctions();
823 QList<const QgsExpressionNode *> lst;
825 lst += mOpLeft->nodes() + mOpRight->nodes();
831 return mOpLeft->needsGeometry() || mOpRight->needsGeometry();
843 const bool leftStatic = mOpLeft->
isStatic( parent, context );
844 const bool rightStatic = mOpRight->isStatic( parent, context );
846 if ( leftStatic && rightStatic )
858 mOpLeft->prepare( parent, context );
859 if ( mOpLeft->hasCachedStaticValue() )
861 QgsExpressionUtils::TVL tvl = QgsExpressionUtils::getTVLValue( mOpLeft->cachedStaticValue(), parent );
862 if ( !parent->
hasEvalError() && tvl == QgsExpressionUtils::True )
870 else if ( rightStatic )
872 mOpRight->prepare( parent, context );
873 if ( mOpRight->hasCachedStaticValue() )
875 QgsExpressionUtils::TVL tvl = QgsExpressionUtils::getTVLValue( mOpRight->cachedStaticValue(), parent );
876 if ( !parent->
hasEvalError() && tvl == QgsExpressionUtils::True )
894 mOpLeft->prepare( parent, context );
895 if ( mOpLeft->hasCachedStaticValue() )
897 QgsExpressionUtils::TVL tvl = QgsExpressionUtils::getTVLValue( mOpLeft->cachedStaticValue(), parent );
898 if ( !parent->
hasEvalError() && tvl == QgsExpressionUtils::False )
906 else if ( rightStatic )
908 mOpRight->prepare( parent, context );
909 if ( mOpRight->hasCachedStaticValue() )
911 QgsExpressionUtils::TVL tvl = QgsExpressionUtils::getTVLValue( mOpRight->cachedStaticValue(), parent );
912 if ( !parent->
hasEvalError() && tvl == QgsExpressionUtils::False )
955 if ( mList->count() == 0 )
956 return mNotIn ? TVL_True : TVL_False;
957 QVariant v1 = mNode->eval( parent, context );
959 if ( QgsExpressionUtils::isNull( v1 ) )
962 bool listHasNull =
false;
964 const QList< QgsExpressionNode * > nodeList = mList->list();
967 QVariant v2 = n->eval( parent, context );
969 if ( QgsExpressionUtils::isNull( v2 ) )
975 if ( ( v1.type() != QVariant::String || v2.type() != QVariant::String ) &&
976 QgsExpressionUtils::isDoubleSafe( v1 ) && QgsExpressionUtils::isDoubleSafe( v2 ) )
980 double f1 = QgsExpressionUtils::getDoubleValue( v1, parent );
982 double f2 = QgsExpressionUtils::getDoubleValue( v2, parent );
988 QString s1 = QgsExpressionUtils::getStringValue( v1, parent );
990 QString s2 = QgsExpressionUtils::getStringValue( v2, parent );
992 equal = QString::compare( s1, s2 ) == 0;
996 return mNotIn ? TVL_False : TVL_True;
1004 return mNotIn ? TVL_True : TVL_False;
1020 bool res = mNode->prepare( parent, context );
1021 const QList< QgsExpressionNode * > nodeList = mList->list();
1024 res = res && n->prepare( parent, context );
1031 return QStringLiteral(
"%1 %2 IN (%3)" ).arg( mNode->dump(), mNotIn ?
"NOT" :
"", mList->dump() );
1043 if ( !mNode->isStatic( parent, context ) )
1046 const QList< QgsExpressionNode * > nodeList = mList->
list();
1049 if ( !n->isStatic( parent, context ) )
1060 QString name = QgsExpression::QgsExpression::Functions()[mFnIndex]->name();
1063 QVariant res = fd->
run( mArgs, context, parent,
this );
1071 : mFnIndex( fnIndex )
1076 QMutexLocker locker( &QgsExpression::QgsExpression::sFunctionsMutex );
1079 const int functionParamsSize = functionParams.size();
1080 if ( functionParams.isEmpty() )
1089 mArgs->
reserve( functionParamsSize );
1099 mArgs->
reserve( functionParamsSize );
1102 const QStringList argNames =
args->
names();
1103 const QList<QgsExpressionNode *> argList =
args->
list();
1106 const int argNamesSize = argNames.size();
1107 while ( idx < argNamesSize && argNames.at( idx ).isEmpty() )
1109 mArgs->
append( argList.at( idx )->clone() );
1115 for ( ; idx < functionParamsSize; ++idx )
1118 int nodeIdx = argNames.indexOf( parameter.
name().toLower() );
1126 mArgs->
append( argList.at( nodeIdx )->clone() );
1148 bool res = fd->
prepare(
this, parent, context );
1151 const QList< QgsExpressionNode * > nodeList = mArgs->
list();
1154 res = res && n->prepare( parent, context );
1164 return QStringLiteral(
"%1%2" ).arg( fd->
name(), fd->
name().startsWith(
'$' ) ? QString() : QStringLiteral(
"()" ) );
1166 return QStringLiteral(
"%1(%2)" ).arg( fd->
name(), mArgs ? mArgs->
dump() : QString() );
1172 return QSet< QString >();
1180 return functionColumns;
1184 const QList< QgsExpressionNode * > nodeList = mArgs->
list();
1187 if ( fd->
parameters().count() <= paramIndex || !fd->
parameters().at( paramIndex ).isSubExpression() )
1188 functionColumns.unite( n->referencedColumns() );
1192 return functionColumns;
1198 if ( fd->
name() == QLatin1String(
"var" ) )
1200 if ( !mArgs->
list().isEmpty() )
1204 return QSet<QString>() << var->
value().toString();
1206 return QSet<QString>() << QString();
1210 QSet<QString> functionVariables = QSet<QString>();
1213 return functionVariables;
1215 const QList< QgsExpressionNode * > nodeList = mArgs->
list();
1218 functionVariables.unite( n->referencedVariables() );
1221 return functionVariables;
1228 QSet<QString> functions = QSet<QString>();
1229 functions.insert( fd->
name() );
1234 const QList< QgsExpressionNode * > nodeList = mArgs->
list();
1237 functions.unite( n->referencedFunctions() );
1244 QList<const QgsExpressionNode *> lst;
1249 const QList< QgsExpressionNode * > nodeList = mArgs->
list();
1259 bool needs = QgsExpression::QgsExpression::Functions()[mFnIndex]->usesGeometry(
this );
1262 const QList< QgsExpressionNode * > nodeList = mArgs->
list();
1264 needs |= n->needsGeometry();
1287 if ( functionParams.isEmpty() )
1294 QSet< int > providedArgs;
1295 QSet< int > handledArgs;
1298 while (
args->
names().at( idx ).isEmpty() )
1300 providedArgs << idx;
1306 for ( ; idx < functionParams.count(); ++idx )
1308 int nodeIdx =
args->
names().indexOf( functionParams.at( idx ).name().toLower() );
1311 if ( !functionParams.at( idx ).optional() )
1313 error = QStringLiteral(
"No value specified for QgsExpressionFunction::Parameter '%1' for %2" ).arg( functionParams.at( idx ).name(),
QgsExpression::Functions()[
fnIndex]->name() );
1319 if ( providedArgs.contains( idx ) )
1321 error = QStringLiteral(
"Duplicate QgsExpressionFunction::Parameter specified for '%1' for %2" ).arg( functionParams.at( idx ).name(),
QgsExpression::Functions()[
fnIndex]->name() );
1325 providedArgs << idx;
1326 handledArgs << nodeIdx;
1331 const QStringList nameList =
args->
names();
1332 for (
const QString &name : nameList )
1334 if ( !name.isEmpty() && !functionParams.contains( name ) )
1339 if ( !name.isEmpty() && !handledArgs.contains( idx ) )
1341 int functionIdx = functionParams.indexOf( name );
1342 if ( providedArgs.contains( functionIdx ) )
1344 error = QStringLiteral(
"Duplicate QgsExpressionFunction::Parameter specified for '%1' for %2" ).arg( functionParams.at( functionIdx ).name(),
QgsExpression::Functions()[
fnIndex]->name() );
1380 return QStringLiteral(
"NULL" );
1382 switch ( mValue.type() )
1385 return QString::number( mValue.toInt() );
1386 case QVariant::Double:
1387 return QString::number( mValue.toDouble() );
1388 case QVariant::LongLong:
1389 return QString::number( mValue.toLongLong() );
1390 case QVariant::String:
1392 case QVariant::Time:
1394 case QVariant::Date:
1396 case QVariant::DateTime:
1398 case QVariant::Bool:
1399 return mValue.toBool() ? QStringLiteral(
"TRUE" ) : QStringLiteral(
"FALSE" );
1401 return tr(
"[unsupported type: %1; value: %2]" ).arg( mValue.typeName(), mValue.toString() );
1412 return QSet<QString>();
1417 return QSet<QString>();
1422 return QSet<QString>();
1427 QList<const QgsExpressionNode *> lst;
1480 parent->
setEvalErrorString( tr(
"No feature available for field '%1' evaluation" ).arg( mName ) );
1517 const thread_local QRegularExpression re( QStringLiteral(
"^[A-Za-z_\\x80-\\xff][A-Za-z0-9_\\x80-\\xff]*$" ) );
1518 const QRegularExpressionMatch match = re.match( mName );
1524 return QSet<QString>() << mName;
1529 return QSet<QString>();
1534 return QSet<QString>();
1539 QList<const QgsExpressionNode *> result;
1566 : mConditions( *conditions )
1567 , mElseExp( elseExp )
1575 qDeleteAll( mConditions );
1585 for (
WhenThen *cond : std::as_const( mConditions ) )
1587 QVariant vWhen = cond->mWhenExp->eval( parent, context );
1588 QgsExpressionUtils::TVL tvl = QgsExpressionUtils::getTVLValue( vWhen, parent );
1590 if ( tvl == QgsExpressionUtils::True )
1592 QVariant vRes = cond->mThenExp->eval( parent, context );
1600 QVariant vElse = mElseExp->
eval( parent, context );
1611 bool foundAnyNonStaticConditions =
false;
1612 for (
WhenThen *cond : std::as_const( mConditions ) )
1614 const bool res = cond->mWhenExp->prepare( parent, context )
1615 && cond->mThenExp->prepare( parent, context );
1619 foundAnyNonStaticConditions |= !cond->mWhenExp->hasCachedStaticValue();
1620 if ( !foundAnyNonStaticConditions && QgsExpressionUtils::getTVLValue( cond->mWhenExp->cachedStaticValue(), parent ) == QgsExpressionUtils::True )
1624 if ( cond->mThenExp->hasCachedStaticValue() )
1643 const bool res = mElseExp->
prepare( parent, context );
1647 if ( !foundAnyNonStaticConditions )
1671 QString msg( QStringLiteral(
"CASE" ) );
1672 for (
WhenThen *cond : mConditions )
1674 msg += QStringLiteral(
" WHEN %1 THEN %2" ).arg( cond->mWhenExp->dump(), cond->mThenExp->dump() );
1677 msg += QStringLiteral(
" ELSE %1" ).arg( mElseExp->
dump() );
1678 msg += QLatin1String(
" END" );
1685 return QSet< QString >();
1688 for (
WhenThen *cond : mConditions )
1690 lst += cond->mWhenExp->referencedColumns() + cond->mThenExp->referencedColumns();
1702 for (
WhenThen *cond : mConditions )
1704 lst += cond->mWhenExp->referencedVariables() + cond->mThenExp->referencedVariables();
1716 for (
WhenThen *cond : mConditions )
1718 lst += cond->mWhenExp->referencedFunctions() + cond->mThenExp->referencedFunctions();
1729 QList<const QgsExpressionNode *> lst;
1731 for (
WhenThen *cond : mConditions )
1733 lst += cond->mWhenExp->nodes() + cond->mThenExp->nodes();
1737 lst += mElseExp->
nodes();
1744 for (
WhenThen *cond : mConditions )
1746 if ( cond->mWhenExp->needsGeometry() ||
1747 cond->mThenExp->needsGeometry() )
1770 if ( !wt->mWhenExp->isStatic( parent, context ) || !wt->mThenExp->isStatic( parent, context ) )
1775 return mElseExp->
isStatic( parent, context );
1783 return QSet< QString >();
1786 const QList< QgsExpressionNode * > nodeList = mList->
list();
1788 lst.unite( n->referencedColumns() );
1795 const QList< QgsExpressionNode * > nodeList = mList->
list();
1797 lst.unite( n->referencedVariables() );
1804 const QList< QgsExpressionNode * > nodeList = mList->
list();
1806 lst.unite( n->referencedFunctions() );
1812 QList<const QgsExpressionNode *> lst;
1814 const QList< QgsExpressionNode * > nodeList = mList->
list();
1825 delete mHigherBound;
1835 bool res = mNode->
prepare( parent, context );
1836 res = res && mLowerBound->
prepare( parent, context );
1837 res = res && mHigherBound->
prepare( parent, context );
1843 const QVariant nodeVal = mNode->
eval( parent, context );
1852 const QVariant lowBoundValue = lowBound.
eval( parent, context );
1853 const bool lowBoundBool { lowBoundValue.toBool() };
1857 return QVariant( mNegate );
1861 const QVariant highBoundValue = highBound.
eval( parent, context );
1868 const bool highBoundBool { highBoundValue.toBool() };
1878 return QVariant( mNegate );
1888 return QVariant( mNegate );
1891 const bool res { lowBoundBool &&highBoundBool };
1892 return mNegate ? QVariant( ! res ) : QVariant( res );
1898 return QStringLiteral(
"%1 %2 %3 AND %4" ).arg( mNode->
dump(), mNegate ? QStringLiteral(
"NOT BETWEEN" ) : QStringLiteral(
"BETWEEN" ), mLowerBound->
dump(), mHigherBound->
dump() );
1919 return {
this, mLowerBound, mHigherBound };
1953 if ( !mNode->
isStatic( parent, context ) )
1956 if ( !mLowerBound->
isStatic( parent, context ) )
1959 if ( !mHigherBound->
isStatic( parent, context ) )
1972 return mHigherBound;
1981 : mWhenExp( whenExp )
1982 , mThenExp( thenExp )
1994 return new WhenThen( mWhenExp->clone(), mThenExp->clone() );
1999 return BINARY_OPERATOR_TEXT[mOp];
2006 const QVariant container = mContainer->eval( parent, context );
2008 const QVariant index = mIndex->eval( parent, context );
2011 switch ( container.type() )
2014 return QgsExpressionUtils::getMapValue( container, parent ).value( index.toString() );
2016 case QVariant::List:
2017 case QVariant::StringList:
2019 const QVariantList list = QgsExpressionUtils::getListValue( container, parent );
2020 qlonglong pos = QgsExpressionUtils::getIntValue( index, parent );
2021 if ( pos >= list.length() || pos < -list.length() )
2028 pos += list.length();
2031 return list.at( pos );
2036 parent->
setEvalErrorString( tr(
"[] can only be used with map or array values, not %1" ).arg( QMetaType::typeName( container.type() ) ) );
2048 bool resC = mContainer->prepare( parent, context );
2049 bool resV = mIndex->prepare( parent, context );
2050 return resC && resV;
2055 return QStringLiteral(
"%1[%2]" ).arg( mContainer->dump(), mIndex->dump() );
2061 return QSet< QString >();
2063 return mContainer->referencedColumns() + mIndex->referencedColumns();
2068 return mContainer->referencedVariables() + mIndex->referencedVariables();
2073 return mContainer->referencedFunctions() + mIndex->referencedFunctions();
2078 QList<const QgsExpressionNode *> lst;
2080 lst += mContainer->nodes() + mIndex->nodes();
2086 return mContainer->needsGeometry() || mIndex->needsGeometry();
2098 return mContainer->
isStatic( parent, context ) && mIndex->isStatic( parent, context );
Expression contexts are used to encapsulate the parameters around which a QgsExpression should be eva...
bool hasFunction(const QString &name) const
Checks whether a specified function is contained in the context.
QgsFeature feature() const
Convenience function for retrieving the feature for the context, if set.
static const QString EXPR_FIELDS
Inbuilt variable name for fields storage.
bool hasVariable(const QString &name) const
Check whether a variable is specified by any scope within the context.
QgsExpressionFunction * function(const QString &name) const
Fetches a matching function from the context.
QVariant variable(const QString &name) const
Fetches a matching variable from the context.
bool hasFeature() const
Returns true if the context has a feature associated with it.
Represents a single parameter passed to a function.
QVariant defaultValue() const
Returns the default value for the parameter.
QString name() const
Returns the name of the parameter.
A abstract base class for defining QgsExpression functions.
QList< QgsExpressionFunction::Parameter > ParameterList
List of parameters, used for function definition.
int params() const
The number of parameters this function takes.
bool lazyEval() const
true if this function should use lazy evaluation.
QString name() const
The name of the function.
virtual QVariant run(QgsExpressionNode::NodeList *args, const QgsExpressionContext *context, QgsExpression *parent, const QgsExpressionNodeFunction *node)
Evaluates the function, first evaluating all required arguments before passing them to the function's...
const QgsExpressionFunction::ParameterList & parameters() const
Returns the list of named parameters for the function, if set.
virtual QSet< QString > referencedColumns(const QgsExpressionNodeFunction *node) const
Returns a set of field names which are required for this function.
virtual bool prepare(const QgsExpressionNodeFunction *node, QgsExpression *parent, const QgsExpressionContext *context) const
This will be called during the prepare step() of an expression if it is not static.
SQL-like BETWEEN and NOT BETWEEN predicates.
bool prepareNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual preparation method Errors are reported to the parent.
QSet< QString > referencedFunctions() const override
Returns a set of all functions which are used in this expression.
bool negate() const
Returns true if the predicate is an exclusion test (NOT BETWEEN).
QgsExpressionNode * lowerBound() const
Returns the lower bound expression node of the range.
QgsExpressionNode::NodeType nodeType() const override
Gets the type of this node.
QSet< QString > referencedVariables() const override
Returns a set of all variables which are used in this expression.
QgsExpressionNode * clone() const override
Generate a clone of this node.
QString dump() const override
Dump this node into a serialized (part) of an expression.
QSet< QString > referencedColumns() const override
Abstract virtual method which returns a list of columns required to evaluate this node.
bool isStatic(QgsExpression *parent, const QgsExpressionContext *context) const override
Returns true if this node can be evaluated for a static value.
QgsExpressionNode * higherBound() const
Returns the higher bound expression node of the range.
QList< const QgsExpressionNode * > nodes() const override
Returns a list of all nodes which are used in this expression.
~QgsExpressionNodeBetweenOperator() override
QVariant evalNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual eval method Errors are reported to the parent.
bool needsGeometry() const override
Abstract virtual method which returns if the geometry is required to evaluate this expression.
A binary expression operator, which operates on two values.
QVariant evalNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual eval method Errors are reported to the parent.
QList< const QgsExpressionNode * > nodes() const override
Returns a list of all nodes which are used in this expression.
bool needsGeometry() const override
Abstract virtual method which returns if the geometry is required to evaluate this expression.
bool leftAssociative() const
Returns true if the operator is left-associative.
QSet< QString > referencedVariables() const override
Returns a set of all variables which are used in this expression.
bool isStatic(QgsExpression *parent, const QgsExpressionContext *context) const override
Returns true if this node can be evaluated for a static value.
int precedence() const
Returns the precedence index for the operator.
QSet< QString > referencedFunctions() const override
Returns a set of all functions which are used in this expression.
QString dump() const override
Dump this node into a serialized (part) of an expression.
QSet< QString > referencedColumns() const override
Abstract virtual method which returns a list of columns required to evaluate this node.
QgsExpressionNode * clone() const override
Generate a clone of this node.
QString text() const
Returns a the name of this operator without the operands.
bool prepareNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual preparation method Errors are reported to the parent.
QgsExpressionNode::NodeType nodeType() const override
Gets the type of this node.
An expression node which takes it value from a feature's field.
bool isStatic(QgsExpression *parent, const QgsExpressionContext *context) const override
Returns true if this node can be evaluated for a static value.
QList< const QgsExpressionNode * > nodes() const override
Returns a list of all nodes which are used in this expression.
QgsExpressionNode::NodeType nodeType() const override
Gets the type of this node.
bool prepareNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual preparation method Errors are reported to the parent.
bool needsGeometry() const override
Abstract virtual method which returns if the geometry is required to evaluate this expression.
QSet< QString > referencedColumns() const override
Abstract virtual method which returns a list of columns required to evaluate this node.
QSet< QString > referencedFunctions() const override
Returns a set of all functions which are used in this expression.
QVariant evalNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual eval method Errors are reported to the parent.
QString dump() const override
Dump this node into a serialized (part) of an expression.
QgsExpressionNode * clone() const override
Generate a clone of this node.
QSet< QString > referencedVariables() const override
Returns a set of all variables which are used in this expression.
Represents a "WHEN... THEN..." portation of a CASE WHEN clause in an expression.
WhenThen(QgsExpressionNode *whenExp, QgsExpressionNode *thenExp)
A combination of when and then.
QgsExpressionNodeCondition::WhenThen * clone() const
Gets a deep copy of this WhenThen combination.
An expression node for CASE WHEN clauses.
QList< QgsExpressionNodeCondition::WhenThen * > WhenThenList
QgsExpressionNodeCondition(QgsExpressionNodeCondition::WhenThenList *conditions, QgsExpressionNode *elseExp=nullptr)
Create a new node with the given list of conditions and an optional elseExp expression.
QSet< QString > referencedVariables() const override
Returns a set of all variables which are used in this expression.
bool needsGeometry() const override
Abstract virtual method which returns if the geometry is required to evaluate this expression.
QString dump() const override
Dump this node into a serialized (part) of an expression.
QVariant evalNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual eval method Errors are reported to the parent.
bool isStatic(QgsExpression *parent, const QgsExpressionContext *context) const override
Returns true if this node can be evaluated for a static value.
QgsExpressionNode::NodeType nodeType() const override
Gets the type of this node.
QgsExpressionNode * clone() const override
Generate a clone of this node.
bool prepareNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual preparation method Errors are reported to the parent.
WhenThenList conditions() const
The list of WHEN THEN expression parts of the expression.
QSet< QString > referencedFunctions() const override
Returns a set of all functions which are used in this expression.
~QgsExpressionNodeCondition() override
QList< const QgsExpressionNode * > nodes() const override
Returns a list of all nodes which are used in this expression.
QSet< QString > referencedColumns() const override
Abstract virtual method which returns a list of columns required to evaluate this node.
An expression node for expression functions.
int fnIndex() const
Returns the index of the node's function.
QSet< QString > referencedFunctions() const override
Returns a set of all functions which are used in this expression.
QgsExpressionNode::NodeList * args() const
Returns a list of arguments specified for the function.
QSet< QString > referencedColumns() const override
Abstract virtual method which returns a list of columns required to evaluate this node.
~QgsExpressionNodeFunction() override
bool isStatic(QgsExpression *parent, const QgsExpressionContext *context) const override
Returns true if this node can be evaluated for a static value.
QList< const QgsExpressionNode * > nodes() const override
Returns a list of all nodes which are used in this expression.
QVariant evalNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual eval method Errors are reported to the parent.
bool prepareNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual preparation method Errors are reported to the parent.
QgsExpressionNodeFunction(int fnIndex, QgsExpressionNode::NodeList *args)
A function node consists of an index of the function in the global function array and a list of argum...
QgsExpressionNode * clone() const override
Generate a clone of this node.
QString dump() const override
Dump this node into a serialized (part) of an expression.
QSet< QString > referencedVariables() const override
Returns a set of all variables which are used in this expression.
QgsExpressionNode::NodeType nodeType() const override
Gets the type of this node.
bool needsGeometry() const override
Abstract virtual method which returns if the geometry is required to evaluate this expression.
static bool validateParams(int fnIndex, QgsExpressionNode::NodeList *args, QString &error)
Tests whether the provided argument list is valid for the matching function.
An expression node for value IN or NOT IN clauses.
bool needsGeometry() const override
Abstract virtual method which returns if the geometry is required to evaluate this expression.
QSet< QString > referencedColumns() const override
Abstract virtual method which returns a list of columns required to evaluate this node.
QList< const QgsExpressionNode * > nodes() const override
Returns a list of all nodes which are used in this expression.
~QgsExpressionNodeInOperator() override
bool prepareNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual preparation method Errors are reported to the parent.
QVariant evalNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual eval method Errors are reported to the parent.
bool isStatic(QgsExpression *parent, const QgsExpressionContext *context) const override
Returns true if this node can be evaluated for a static value.
QString dump() const override
Dump this node into a serialized (part) of an expression.
QSet< QString > referencedVariables() const override
Returns a set of all variables which are used in this expression.
QSet< QString > referencedFunctions() const override
Returns a set of all functions which are used in this expression.
QgsExpressionNode::NodeType nodeType() const override
Gets the type of this node.
QgsExpressionNode * clone() const override
Generate a clone of this node.
QgsExpressionNode::NodeList * list() const
Returns the list of nodes to search for matching values within.
A indexing expression operator, which allows use of square brackets [] to reference map and array ite...
QVariant evalNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual eval method Errors are reported to the parent.
bool needsGeometry() const override
Abstract virtual method which returns if the geometry is required to evaluate this expression.
QSet< QString > referencedColumns() const override
Abstract virtual method which returns a list of columns required to evaluate this node.
bool isStatic(QgsExpression *parent, const QgsExpressionContext *context) const override
Returns true if this node can be evaluated for a static value.
QgsExpressionNode * clone() const override
Generate a clone of this node.
QString dump() const override
Dump this node into a serialized (part) of an expression.
QSet< QString > referencedFunctions() const override
Returns a set of all functions which are used in this expression.
QList< const QgsExpressionNode * > nodes() const override
Returns a list of all nodes which are used in this expression.
QgsExpressionNode::NodeType nodeType() const override
Gets the type of this node.
bool prepareNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual preparation method Errors are reported to the parent.
QSet< QString > referencedVariables() const override
Returns a set of all variables which are used in this expression.
An expression node for literal values.
QList< const QgsExpressionNode * > nodes() const override
Returns a list of all nodes which are used in this expression.
QSet< QString > referencedColumns() const override
Abstract virtual method which returns a list of columns required to evaluate this node.
QString dump() const override
Dump this node into a serialized (part) of an expression.
QgsExpressionNode::NodeType nodeType() const override
Gets the type of this node.
QSet< QString > referencedFunctions() const override
Returns a set of all functions which are used in this expression.
QString valueAsString() const
Returns a string representation of the node's literal value.
QSet< QString > referencedVariables() const override
Returns a set of all variables which are used in this expression.
QVariant evalNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual eval method Errors are reported to the parent.
bool prepareNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual preparation method Errors are reported to the parent.
QgsExpressionNode * clone() const override
Generate a clone of this node.
bool isStatic(QgsExpression *parent, const QgsExpressionContext *context) const override
Returns true if this node can be evaluated for a static value.
bool needsGeometry() const override
Abstract virtual method which returns if the geometry is required to evaluate this expression.
QVariant value() const
The value of the literal.
A unary node is either negative as in boolean (not) or as in numbers (minus).
QgsExpressionNode::NodeType nodeType() const override
Gets the type of this node.
bool prepareNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual preparation method Errors are reported to the parent.
QSet< QString > referencedFunctions() const override
Returns a set of all functions which are used in this expression.
QgsExpressionNodeUnaryOperator::UnaryOperator op() const
Returns the unary operator.
QSet< QString > referencedColumns() const override
Abstract virtual method which returns a list of columns required to evaluate this node.
QList< const QgsExpressionNode * > nodes() const override
Returns a list of all nodes which are used in this expression.
QString text() const
Returns a the name of this operator without the operands.
bool isStatic(QgsExpression *parent, const QgsExpressionContext *context) const override
Returns true if this node can be evaluated for a static value.
QVariant evalNode(QgsExpression *parent, const QgsExpressionContext *context) override
Abstract virtual eval method Errors are reported to the parent.
bool needsGeometry() const override
Abstract virtual method which returns if the geometry is required to evaluate this expression.
QgsExpressionNode * clone() const override
Generate a clone of this node.
QString dump() const override
Dump this node into a serialized (part) of an expression.
QSet< QString > referencedVariables() const override
Returns a set of all variables which are used in this expression.
A list of expression nodes.
bool hasNamedNodes() const
Returns true if list contains any named nodes.
virtual QString dump() const
Returns a string dump of the expression node.
QStringList names() const
Returns a list of names for nodes.
QgsExpressionNode::NodeList * clone() const
Creates a deep copy of this list. Ownership is transferred to the caller.
void append(QgsExpressionNode *node)
Takes ownership of the provided node.
void reserve(int size)
Reserves size for the node list.
QList< QgsExpressionNode * > list()
Gets a list of all the nodes.
Abstract base class for all nodes that can appear in an expression.
bool hasCachedStaticValue() const
Returns true if the node can be replaced by a static cached value.
virtual QString dump() const =0
Dump this node into a serialized (part) of an expression.
QVariant eval(QgsExpression *parent, const QgsExpressionContext *context)
Evaluate this node with the given context and parent.
virtual QgsExpressionNode * clone() const =0
Generate a clone of this node.
virtual bool isStatic(QgsExpression *parent, const QgsExpressionContext *context) const =0
Returns true if this node can be evaluated for a static value.
bool prepare(QgsExpression *parent, const QgsExpressionContext *context)
Prepare this node for evaluation.
virtual QSet< QString > referencedColumns() const =0
Abstract virtual method which returns a list of columns required to evaluate this node.
bool mHasCachedValue
true if the node has a static, precalculated value.
const QgsExpressionNode * effectiveNode() const
Returns a reference to the simplest node which represents this node, after any compilation optimizati...
QVariant cachedStaticValue() const
Returns the node's static cached value.
virtual QSet< QString > referencedVariables() const =0
Returns a set of all variables which are used in this expression.
QVariant mCachedStaticValue
Contains the static, precalculated value for the node if mHasCachedValue is true.
std::unique_ptr< QgsExpressionNode > mCompiledSimplifiedNode
Contains a compiled node which represents a simplified version of this node as a result of compilatio...
NodeType
Known node types.
@ ntBetweenOperator
Between operator.
@ ntIndexOperator
Index operator.
virtual bool needsGeometry() const =0
Abstract virtual method which returns if the geometry is required to evaluate this expression.
virtual QList< const QgsExpressionNode * > nodes() const =0
Returns a list of all nodes which are used in this expression.
void cloneTo(QgsExpressionNode *target) const
Copies the members of this node to the node provided in target.
virtual QSet< QString > referencedFunctions() const =0
Returns a set of all functions which are used in this expression.
Class for parsing and evaluation of expressions (formerly called "search strings").
static const QList< QgsExpressionFunction * > & Functions()
static QString quotedString(QString text)
Returns a quoted version of a string (in single quotes)
void setEvalErrorString(const QString &str)
Sets evaluation error (used internally by evaluation functions)
static QString quotedColumnRef(QString name)
Returns a quoted column reference (in double quotes)
bool hasEvalError() const
Returns true if an error occurred when evaluating last input.
The feature class encapsulates a single feature including its unique ID, geometry and a list of field...
int fieldNameIndex(const QString &fieldName) const
Utility method to get attribute index from name.
bool isValid() const
Returns the validity of this feature.
QVariant attribute(const QString &name) const
Lookup attribute value by attribute name.
Container of fields for a vector layer.
int lookupField(const QString &fieldName) const
Looks up field's index from the field name.
A representation of the interval between two datetime values.
double seconds() const
Returns the interval duration in seconds.
static QString qRegExpEscape(const QString &string)
Returns an escaped string matching the behavior of QRegExp::escape.
static bool isNull(const QVariant &variant)
Returns true if the specified variant should be considered a NULL value.
bool qgsDoubleNear(double a, double b, double epsilon=4 *std::numeric_limits< double >::epsilon())
Compare two doubles (but allow some difference)
#define ENSURE_NO_EVAL_ERROR
#define SET_EVAL_ERROR(x)
QgsExpressionNode * node
Node.