Basic Powershell Parser

ptimothyp@gmail.com Avatar

Main Parser


class Parser {
    [string[]]$Tokens
    [int]$Position = 0

    Parser([string]$input) {
        # Tokenize: split by spaces but keep parentheses
        $this.Tokens = $input.Replace('(',' ( ').Replace(')',' ) ').Split(' ', [System.StringSplitOptions]::RemoveEmptyEntries)
    }

    [string] Peek() {
        if ($this.Position -lt $this.Tokens.Count) { return $this.Tokens[$this.Position] }
        return $null
    }

    [string] Consume() {
        return $this.Tokens[$this.Position++]
    }

    # Level 1: OR (Lowest precedence)
    [hashtable] ParseExpression() {
        $node = $this.ParseTerm()

        while ($this.Peek() -eq "OR") {
            $operator = $this.Consume()
            $right = $this.ParseTerm()
            $node = @{ Operator = $operator; Left = $node; Right = $right }
        }
        return $node
    }

    # Level 2: AND
    [hashtable] ParseTerm() {
        $node = $this.ParseFactor()

        while ($this.Peek() -eq "AND") {
            $operator = $this.Consume()
            $right = $this.ParseFactor()
            $node = @{ Operator = $operator; Left = $node; Right = $right }
        }
        return $node
    }

    # Level 3: Values and Parentheses (Highest precedence)
    [hashtable] ParseFactor() {
        $token = $this.Consume()

        if ($token -eq "(") {
            $node = $this.ParseExpression()
            [void]$this.Consume() # Consume matching ')'
            return $node
        }

        return @{ Value = $token }
    }
}

Usage

$Query = “Status AND (User OR Admin)”
$Parser = [Parser]::new($Query)
$OutputTree = $Parser.ParseExpression()

Display as JSON to see the nested structure clearly

$OutputTree | ConvertTo-Json -Depth 10

Enjoying this article?

Subscribe to get new posts delivered straight to your inbox. No spam, unsubscribe anytime.

No spam. Unsubscribe anytime.

You may also like

See All Development →