filter.go 1.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869
  1. // +build !nofilter
  2. package filtering
  3. import (
  4. "fmt"
  5. "os"
  6. "github.com/araddon/qlbridge/datasource"
  7. "github.com/araddon/qlbridge/expr"
  8. "github.com/araddon/qlbridge/value"
  9. "github.com/araddon/qlbridge/vm"
  10. )
  11. type ExprValue struct {
  12. node expr.Node
  13. expression string
  14. }
  15. func (e *ExprValue) String() string {
  16. if e.node != nil {
  17. return e.node.String()
  18. } else {
  19. return "<Empty Expression>"
  20. }
  21. }
  22. func (e *ExprValue) Set(value string) error {
  23. if value == "" {
  24. e.node = nil
  25. e.expression = value
  26. return nil
  27. }
  28. ast, err := expr.ParseExpression(value)
  29. if err != nil {
  30. return err
  31. }
  32. e.node = ast
  33. e.expression = value
  34. return nil
  35. }
  36. // Validate answers the question wether to include a log line or not.
  37. func (e *ExprValue) Validate(lineInput map[string]interface{}) bool {
  38. if e.node == nil {
  39. return true
  40. }
  41. line := translateMap(lineInput)
  42. context := datasource.NewContextSimpleNative(line)
  43. val, ok := vm.Eval(context, e.node)
  44. if !ok || val == nil { // errors when evaluating
  45. return false
  46. }
  47. if bv, isBool := val.(value.BoolValue); isBool {
  48. return bv.Val()
  49. }
  50. fmt.Fprintln(os.Stderr, "WARNING: The 'where' expression doesn't return a boolean")
  51. return false
  52. }
  53. func translateMap(lineInput map[string]interface{}) map[string]interface{} {
  54. lineOutput := make(map[string]interface{})
  55. lineOutput["prog"] = lineInput["app_name"]
  56. lineOutput["msg"] = lineInput["message"]
  57. lineOutput["facility"] = lineInput["facility"]
  58. lineOutput["host"] = lineInput["hostname"]
  59. lineOutput["time"] = lineInput["timestamp"]
  60. lineOutput["sev"] = lineInput["severity"]
  61. return lineOutput
  62. }