ogcapi-features icon indicating copy to clipboard operation
ogcapi-features copied to clipboard

CQL2 grammar: BNF definition of function

Open dannbuckley opened this issue 6 months ago • 2 comments

Hello,

I am currently building an implementation of the CQL2-Text spec and had a question about the current definition of the function rule in the BNF schema.

https://github.com/opengeospatial/ogcapi-features/blob/64e26b624a052510b7d10e93b304cad0e5b30194/cql2/standard/schema/cql2.bnf#L355

Based on the rest of the schema, you seem to be using the { ... } brace syntax to signify "1 or more". So, from my current understanding, wouldn't the current rule imply that something like function(arga1, arga2, arga3 <space> argb1, argb2, ...) is valid, with more than one argument list provided?

The closest similar rule I could find is isInListPredicate:

https://github.com/opengeospatial/ogcapi-features/blob/64e26b624a052510b7d10e93b304cad0e5b30194/cql2/standard/schema/cql2.bnf#L101

Here, the inList rule appears without braces and the resulting rule when substituted would be a single instance of scalarExpression [ {"," scalarExpression} ]

I'm wondering whether the argumentList in function should have its braces removed, giving something like:

- function = identifier "(" {argumentList} ")";
+ function = identifier "(" argumentList ")";

# When substituted, this gives:
function = identifier "(" argument [ { "," argument } ] ")";

Thanks in advance!

dannbuckley avatar May 31 '25 14:05 dannbuckley

@dannbuckley I think this is just a typo. This is my Implementation: https://github.com/IndoorSpatial/cql2cpp/blob/7331c03bf0d9cc0dbcc7c518ef096d7df8020434/src/cql2_parser.y#L353

kunlinyu avatar Jun 09 '25 02:06 kunlinyu

@kunlinyu

This seems to be a holdover from previous versions of this rule. Here's the oldest version I could find:

https://github.com/opengeospatial/ogcapi-features/blame/c7f1ec176be3e05d4de8465932f454fea218f12e/extensions/cql/standard/schema/cql.bnf#L131

function = identifier {argumentList};
argumentList = leftParen [positionalArgument] rightParen;
positionalArgument = argument [ { comma argument } ];

I think how you've implemented it is correct, where you can have a function with an empty argument list. The rule should probably be changed to something like this then:

- function = identifier "(" {argumentList} ")";
+ function = identifier "(" [argumentList] ")";

dannbuckley avatar Jun 09 '25 13:06 dannbuckley