Skip to content

Implement grouped logical expressions #40

Description

@Seddryck

Description

Implement grouped logical expressions as first-class syntax.

Expressif currently uses curly braces to group logical expressions, for example:

{starts-with("A") |AND ends-with("Z")}

The Tree-sitter grammar should preserve the grouping explicitly in the CST rather than discarding the delimiters or treating the grouped form as a special predicate type.

Syntax model

Add a dedicated grouping node:

ExpressionSyntax
└── GroupedExpressionSyntax
    └── expression: ExpressionSyntax

For example:

{foo |AND bar}

should conceptually produce:

GroupedExpressionSyntax
└── BinaryExpressionSyntax
    ├── left: FunctionCallSyntax("foo")
    ├── operator: |AND
    └── right: FunctionCallSyntax("bar")

Purpose

Grouping controls the syntactic structure of logical expressions and therefore affects precedence.

Examples:

{a |OR b} |AND c
a |OR {b |AND c}
!{a |OR b}

The grouped expression must remain visible in the CST so later tooling can recover the user's explicit grouping.

Curly-brace disambiguation

Curly braces are already used by several Expressif constructs, including:

{}                     // empty array
{:}                    // empty record
{1,2,3}                // array
{name := "Alice"}      // record
{@value | lower}        // parameterized expression
{foo |AND bar}          // grouped logical expression

The grammar must distinguish these forms structurally, without relying on function names or semantic information.

Generic expression content

A grouped logical expression should contain ordinary expression syntax.

Examples:

{foo |AND bar}
{!foo |OR bar}
{{a |OR b} |AND c}

The parser must not validate whether the enclosed expressions are semantically predicate-compatible.

Whitespace

Whitespace around and inside the grouping delimiters is insignificant except where already significant to nested syntax.

Examples:

{foo |AND bar}
{ foo |AND bar }
{  foo |OR bar  }

Out of scope

Do not implement:

  • predicate/function catalogue lookup;
  • semantic boolean validation;
  • runtime evaluation;
  • semantic lowering;
  • alternative grouping delimiters.

Tests

Add Tree-sitter corpus tests covering at minimum:

  • grouping around a binary expression;
  • grouping containing unary expressions;
  • nested grouping;
  • grouping combined with outer binary expressions;
  • grouping under unary negation;
  • distinction from arrays;
  • distinction from records;
  • distinction from parameterized expressions;
  • whitespace variations;
  • missing closing brace;
  • empty grouping if invalid;
  • CST preservation of explicit grouping.

Tests should assert CST structure, not only parse success.

Architectural constraint

Grouping is syntax. The parser should preserve the delimiters and expression structure while leaving semantic predicate validation to later binding.

Metadata

Metadata

Assignees

No one assigned

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions