Events filter in CCX Notification Service
Why?
- to be able to decide which events to process and send
- to notification service
- to service log
- configurable w/o the need to change the code
- OTOH current situation
// TODO: make this configurable via config file
totalRiskThreshold = 3
Desirable situation
- Event filtering configurable via TOML files and environment variables
[kafka_broker]
enabled = true
address = "kafka:29092"
...
...
...
likelihood_threshold = 0
impact_threshold = 0
severity_threshold = 0
total_risk_threshold = 3
event_filter = "totalRisk >= totalRiskThreshold"
[service_log]
enabled = false
access_token = ""
url = "https://api.openshift.com/api/service_logs/v1/cluster_logs/"
...
...
...
likelihood_threshold = 0
impact_threshold = 3
severity_threshold = 0
total_risk_threshold = 3
event_filter = "totalRisk > totalRiskThreshold && severity > 2*(severityTreshold + impact)"
How?
- DSL
- minimal
- easy to comprehend
- safe!!!
- isolated
- ideally compatible with Go (operator precedence etc.)
- Safe?
- no loops
- no indexing
- no access to variables etc.
- unable to call any function
- just selected ‘named values’
- -> no needs to care about sandboxing
Implementation
- Expression language
- standard operator precedence (Go-compatible)
- parenthesis etc.
- Operators
- arithmetic
- logic
- relational
- Values
- selected values only (like ‘severity’)
- explicitly passed via map in code
Implementation
- Three stages
- expression tokenization
- transform: algebraic -> RPN (postfix)
- RPN (postfix) evaluation
Expression tokenization
- Based on standard Go lexer
- so trivial to implement
- and super safe
- Our implementation
- The famous shunting yard algorithm
- Our implementation
RPN evaluation
- Stack based, trivial to implement
- Our implementation
Values mapping
- Via dictionary (a map)
- No other named values can be used
- Super safe
- no custom (usually broken) sandboxing needed
- Our implementation
- 1 line of code + one extra line for each value to be passed
- Source code
Links