github.com/siglens/siglens@v0.0.0-20240328180423-f7ce9ae441ed/pkg/ast/pipesearch/searchQuery.peg (about)

     1  {
     2  package pipesearch
     3  import (
     4      "strconv"
     5  	"github.com/siglens/siglens/pkg/segment/structs"
     6      "github.com/siglens/siglens/pkg/segment/utils"
     7      "github.com/siglens/siglens/pkg/ast"
     8      "fmt"
     9  )
    10  	// helper method to exfiltrate pigeon's generated error type
    11  func getParseError(err error) error {
    12  	switch ev := err.(type) {
    13  	case errList:
    14  		if pe, ok := ev[0].(*parserError); ok {
    15  			return &ast.ParseError{
    16  				Inner:    pe.Inner,
    17  				Line:     pe.pos.line,
    18  				Column:   pe.pos.col,
    19  				Offset:   pe.pos.offset,
    20  				Prefix:   pe.prefix,
    21  				Expected: pe.expected,
    22  			}
    23  		}
    24  	}
    25  	return err
    26  }
    27  
    28  }
    29  
    30  Start <- maggs:measureAggsList? EOF {
    31          var q ast.QueryStruct
    32          if maggs !=nil {
    33              q.PipeCommands = maggs.(*structs.QueryAggregators)
    34          }
    35          return q, nil
    36  } / groupBy:groupByList? space? lim:Limit? EOF {
    37      var q ast.QueryStruct
    38      if groupBy != nil {
    39          q.PipeCommands = groupBy.(*structs.QueryAggregators)
    40          q.PipeCommands.BucketLimit = groupBy.(*structs.QueryAggregators).BucketLimit
    41      }
    42      return q, nil
    43  
    44  } / query:Query? aggs:AggClause? EOF {
    45      var q ast.QueryStruct
    46      if query !=nil{
    47          q.SearchFilter = query.(*ast.Node)
    48      }
    49      if aggs !=nil {
    50          q.PipeCommands = aggs.(*structs.QueryAggregators)
    51      }
    52      return q, nil
    53  } / query:Query? EOF {
    54      var q ast.QueryStruct
    55      if query !=nil{
    56          q.SearchFilter = query.(*ast.Node)
    57      }
    58      return q, nil
    59  } / aggs:AggClause? EOF {
    60      var q ast.QueryStruct
    61      if aggs !=nil {
    62          q.PipeCommands = aggs.(*structs.QueryAggregators)
    63      }
    64      return q, nil
    65  }
    66  
    67  Query <- _ clause:OrClause _ {
    68      return clause, nil
    69  }
    70  
    71  /****
    72  NODES
    73  *****/
    74  
    75  OrClause <- lhs:AndClause space logicalOR space rhs:OrClause {
    76      return & ast.Node {
    77          NodeType:  ast.NodeOr,
    78          Left: lhs.(*ast.Node),
    79          Right: rhs.(*ast.Node),
    80      }, nil
    81  } / AndClause
    82  
    83  
    84  measureAggsList <- space? first:MeasureAggClause rest:( space? ',' space? MeasureAggClause )* space? {
    85      return ast.GetMeasureAggsTokens(first, rest, 3), nil
    86  }
    87  
    88  groupByList <- space? first:MeasureAggClause rest:( space? ',' space? MeasureAggClause )* space? GroupBy cols:(ColList)? space? lim:Limit? {
    89      limit := int(3000)
    90      if lim != nil {
    91          limit = int(lim.(int64))
    92      }
    93      return ast.GetGroupByTokens(cols, first, rest, 3, limit), nil
    94  }
    95  
    96  Limit <- "limit" space first:Identifier{
    97      limit, err := strconv.ParseInt(first.(string), 10, 64)
    98      if err != nil {
    99          return nil, err
   100      }
   101      return limit, err
   102  }
   103  
   104  
   105  MeasureAggClause <- space? funcs:MeasureAggsFunc '(' cols:Identifier ')' {
   106      
   107  	tempMeasureAgg := &structs.MeasureAggregator{}
   108  	tempMeasureAgg.MeasureCol = cols.(string)
   109  	tempMeasureAgg.MeasureFunc = funcs.(utils.AggregateFunctions)
   110      return tempMeasureAgg, nil
   111  }
   112  
   113  
   114  AggClause <- opPipe space? Column space  newCol:Identifier space? '=' space? oldCol:Identifier {
   115      aggNode := &structs.QueryAggregators{}
   116  	aggNode.PipeCommandType = structs.OutputTransformType
   117  	aggNode.OutputTransforms = &structs.OutputTransforms{}
   118  	aggNode.OutputTransforms.OutputColumns = &structs.ColumnsRequest{}
   119      aggNode.OutputTransforms.OutputColumns.RenameColumns = make(map[string]string)
   120      aggNode.OutputTransforms.OutputColumns.RenameColumns[oldCol.(string)]= newCol.(string)
   121      return aggNode, nil
   122  }
   123  / opPipe space? Column space cols:ColList {
   124      aggNode := &structs.QueryAggregators{}
   125  	aggNode.PipeCommandType = structs.OutputTransformType
   126  	aggNode.OutputTransforms = &structs.OutputTransforms{}
   127  	aggNode.OutputTransforms.OutputColumns = &structs.ColumnsRequest{}
   128      aggNode.OutputTransforms.OutputColumns.IncludeColumns = cols.([]string)
   129      return aggNode, nil
   130  }
   131  / opPipe space? Column space '-' space cols:ColList {
   132      aggNode := &structs.QueryAggregators{}
   133  	aggNode.PipeCommandType = structs.OutputTransformType
   134  	aggNode.OutputTransforms = &structs.OutputTransforms{}
   135  	aggNode.OutputTransforms.OutputColumns = &structs.ColumnsRequest{}
   136      aggNode.OutputTransforms.OutputColumns.ExcludeColumns = cols.([]string)
   137      return aggNode, nil
   138  }
   139  / opPipe space? maggs:measureAggsList EOF{
   140      aggNode := &structs.QueryAggregators{}
   141      aggNode = maggs.(*structs.QueryAggregators)
   142      return aggNode, nil
   143  }
   144  / opPipe space? groupBy:groupByList space? lim:Limit? EOF{
   145      aggNode := &structs.QueryAggregators{}
   146      aggNode = groupBy.(*structs.QueryAggregators)
   147      return aggNode, nil
   148  }
   149  / opPipe space? Let space newCol:Identifier space? '=' space? '('? space? lhs:Identifier space? operation:LetOpr 
   150  space? rhs:LetIdentifier space? ')'? {
   151      aggNode := &structs.QueryAggregators{}
   152  	aggNode.PipeCommandType = structs.OutputTransformType
   153  	aggNode.OutputTransforms = &structs.OutputTransforms{}
   154  	aggNode.OutputTransforms.LetColumns = &structs.LetColumnsRequest{}
   155      aggNode.OutputTransforms.LetColumns.NewColName = newCol.(string)
   156      aggNode.OutputTransforms.LetColumns.SingleColRequest = &structs.SingleColLetRequest{}
   157      aggNode.OutputTransforms.LetColumns.SingleColRequest.CName = lhs.(string)
   158      aggNode.OutputTransforms.LetColumns.SingleColRequest.Oper = operation.(utils.LogicalAndArithmeticOperator)
   159      aggNode.OutputTransforms.LetColumns.SingleColRequest.Value = rhs.(*utils.DtypeEnclosure)
   160      return aggNode, nil
   161  }
   162  / opPipe space? Let space newCol:Identifier space? '=' space? '('? space? lhs:Identifier space? operation:LetOpr 
   163  space? rhs:Identifier space? ')'? {
   164      aggNode := &structs.QueryAggregators{}
   165  	aggNode.PipeCommandType = structs.OutputTransformType
   166  	aggNode.OutputTransforms = &structs.OutputTransforms{}
   167  	aggNode.OutputTransforms.LetColumns = &structs.LetColumnsRequest{}
   168      aggNode.OutputTransforms.LetColumns.NewColName = newCol.(string)
   169      aggNode.OutputTransforms.LetColumns.MultiColsRequest = &structs.MultiColLetRequest{}
   170      aggNode.OutputTransforms.LetColumns.MultiColsRequest.LeftCName = lhs.(string)
   171      aggNode.OutputTransforms.LetColumns.MultiColsRequest.Oper = operation.(utils.LogicalAndArithmeticOperator)
   172      aggNode.OutputTransforms.LetColumns.MultiColsRequest.RightCName = rhs.(string)
   173      return aggNode, nil
   174  }
   175  
   176  MeasureAggsFunc <- mfunc: ("avg" / "min" / "max" / "sum" / "cardinality" / "count" ){
   177      aggFunc, _ := ast.AggTypeToAggregateFunction(string(c.text))
   178      return aggFunc, nil
   179  }
   180  
   181  
   182  Column <- "columns"
   183  
   184  GroupBy <- "groupby"
   185  
   186  Let <- "let"
   187  
   188  LetOpr <- [>] '=' {
   189      return utils.LetGreaterThanOrEqualTo, nil
   190  } / '>' {
   191      return utils.LetGreaterThan, nil
   192  } / [<] '=' {
   193      return utils.LetLessThanOrEqualTo, nil
   194  } / '<' {
   195      return utils.LetLessThan, nil
   196  } / [=] '=' {
   197      return utils.LetEquals, nil
   198  } / [!] '=' {
   199      return utils.LetNotEquals, nil
   200  } / '+' {
   201      return utils.LetAdd, nil
   202  } / '-' {
   203      return utils.LetSubtract, nil
   204  } / '/' {
   205      return utils.LetDivide, nil
   206  } / '*' {
   207      return utils.LetMultiply, nil
   208  } / '%' {
   209      return utils.LetModulo, nil
   210  }
   211  
   212  LetIdentifier <- '-'? Float {
   213      var dte utils.DtypeEnclosure
   214      dte.Dtype = utils.SS_DT_FLOAT
   215      dte.FloatVal,_ = strconv.ParseFloat(string(c.text), 64)
   216      dte.StringVal = string(c.text)
   217      return &dte, nil
   218  } / '-'+ Integer {
   219      var dte utils.DtypeEnclosure
   220      dte.Dtype = utils.SS_DT_SIGNED_NUM
   221      dte.SignedVal,_ = strconv.ParseInt(string(c.text),10, 64)
   222      dte.StringVal = string(c.text)
   223      return &dte, nil
   224  } /  Integer {
   225      var dte utils.DtypeEnclosure
   226      dte.Dtype = utils.SS_DT_UNSIGNED_NUM
   227      dte.UnsignedVal,_ = strconv.ParseUint(string(c.text),10, 64)
   228      dte.StringVal = string(c.text)
   229      return &dte, nil
   230  } / BoolValue {
   231      var dte utils.DtypeEnclosure
   232      dte.Dtype = utils.SS_DT_BOOL
   233      bVal ,_ := strconv.ParseBool(string(c.text))
   234      if bVal == true {
   235  			dte.BoolVal = 1
   236  		} else {
   237  			dte.BoolVal = 0
   238  		}
   239      dte.StringVal = string(c.text)
   240      return &dte, nil
   241  } 
   242  
   243  BoolValue <- "false" / "true"
   244  
   245  Float <- [0-9]+ '.' [0-9]+
   246  
   247  Integer <- [0-9]+
   248  
   249  ColList <-  space? first:Identifier rest:( space? ',' space? Identifier )* space? {
   250      return ast.GetTokens(first, rest, 3), nil
   251  }
   252  
   253  AndClause <- lhs:NotClause space logicalAND space rhs:AndClause {
   254      return &ast.Node {
   255          NodeType: ast.NodeAnd,
   256          Left: lhs.(*ast.Node),
   257          Right: rhs.(*ast.Node),
   258      }, nil
   259  } / NotClause
   260  
   261  NotClause <- logicalNOT cmp:Comparison {
   262      return &ast.Node {
   263          NodeType: ast.NodeNot,
   264          Left: cmp.(*ast.Node),
   265          Right: nil,
   266      }, nil
   267  } / Comparison
   268  
   269  Comparison <- '(' space? query:OrClause space? ')'{
   270      return query, nil
   271  } /  field:Field space?  operation:opCOMP space? field1:Field  {
   272      var opOut string
   273      if operation == nil && field!=nil {
   274          opOut = "="
   275      } else {
   276          opOut = operation.(string)
   277      }
   278      return &ast.Node{
   279          NodeType: ast.NodeTerminal,
   280          Comparison:ast.Comparison{
   281              Op: opOut,
   282              Field: field.(string),
   283              Values: field1,
   284          },
   285      }, nil
   286  } / values:ValueList {
   287      return &ast.Node{
   288          NodeType: ast.NodeTerminal,
   289          Comparison:ast.Comparison{
   290              Op: "=",
   291              Field: "*",
   292              Values: values,
   293          },
   294      }, nil
   295  } / field:Field {
   296      return &ast.Node{
   297          NodeType: ast.NodeTerminal,
   298          Comparison:ast.Comparison{
   299              Op: "=",
   300              Field: "*",
   301              Values: field,
   302          },
   303      }, nil
   304  }
   305  
   306  /*****
   307  FIELDS
   308  ******/
   309  
   310  Field <- Value / pieces:(FieldPiece ('.' FieldPiece)*) {
   311      if pieces == nil {
   312  		return "*", nil
   313  	}
   314  
   315      return string(c.text), nil
   316  }
   317  
   318  FieldPiece <- QuotedFieldPiece / UnquotedFieldPiece / Star
   319  
   320  UnquotedFieldPiece <- [-a-zA-Z0-9$&,?#%_@;[\]{}+-./*:]i+ {
   321      return string(c.text), nil
   322  }
   323  
   324  
   325  QuotedFieldPiece <- QuotedValue
   326  
   327  Star <- '*' {
   328      return "*", nil
   329  }
   330  QuotedValue <- '"' ( !EscapedChar . / '\\' EscapeSequence )* '"' {
   331      c.text = bytes.Replace(c.text, []byte(`\/`), []byte(`/`), -1)
   332      return strconv.Unquote(string(c.text))
   333  }
   334  EscapedChar <- [\x00-\x1f"\\]
   335  
   336  EscapeSequence <- SingleCharEscape / UnicodeEscape
   337  
   338  SingleCharEscape <- ["\\/bfnrt]
   339  
   340  UnicodeEscape <- 'u' HexDigit HexDigit HexDigit HexDigit
   341  
   342  HexDigit <- [0-9a-f]i
   343  
   344  /*****
   345  VALUES
   346  ******/
   347  
   348  ValueList <- '[' space? first:Value rest:( space? ',' space? Value )* space? ']' {
   349      return ast.GetTokens(first, rest, 3), nil
   350  } / value:Value 
   351  
   352  Value <- val:(
   353      Float
   354      / Integer
   355      
   356      ){
   357      return ast.MakeValue(val)
   358    }
   359  
   360  String
   361    = '"' chars:[^"]* '"' {
   362      return ast.StringFromChars(chars), nil
   363    } 
   364  
   365  Integer <- [+-]? [0-9]+ {
   366      return json.Number(string(c.text)), nil
   367    }
   368  
   369  Float <- [+-]? ([0-9]* "." [0-9]+ ) {
   370        return json.Number(string(c.text)), nil
   371      }
   372  
   373  
   374  Identifier <-
   375     [a-zA-Z0-9_@./*]i+ { 
   376        return string(c.text), nil
   377  }
   378  
   379  
   380  opPipe <- "|" 
   381  
   382  /****************
   383  LOGICAL OPERATORS
   384  *****************/
   385  
   386  logicalOR <- "OR"
   387  
   388  logicalAND <- "AND"
   389  
   390  logicalNOT <- "NOT" space / '!' space?
   391  
   392  /*******************
   393  COMPARISON OPERATORS
   394  ********************/
   395  
   396  
   397  
   398  opCOMP <- opCustom
   399  / "<=" {
   400      return string(c.text), nil
   401  } / ">=" {
   402      return string(c.text), nil
   403  } / "=" {
   404      return string(c.text), nil
   405  } / "<" {
   406      return string(c.text), nil
   407  } / ">" {
   408      return string(c.text), nil
   409  } / "!=" {
   410      return string(c.text), nil
   411    }
   412  
   413  
   414  opCustom <- '=' opname:[a-z]i+ '='{
   415      return ast.OpNameToString(opname)
   416  }
   417  
   418  /**********************
   419  WHITESPACE AND TERMINAL
   420  ***********************/
   421  
   422  _ "whitespace" <- [ \n\t\r]*
   423  
   424  space <- [ \n\t\r]+
   425  
   426  EOL <- '\n'
   427  
   428  EOF = !.
   429  
   430  /*****************************
   431  TERMINAL ERROR HANDLING STATES
   432  ******************************/
   433  
   434  /*
   435  ErrOp <- #{
   436      return fmt.Errorf("invalid operator")
   437  }
   438  */