-
Notifications
You must be signed in to change notification settings - Fork 1.2k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add type field to AlertingRule and RecordingRule struct #1558
base: main
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -601,6 +601,7 @@ type AlertingRule struct { | |
EvaluationTime float64 `json:"evaluationTime"` | ||
LastEvaluation time.Time `json:"lastEvaluation"` | ||
State string `json:"state"` | ||
Type string `json:"type"` | ||
} | ||
|
||
// RecordingRule models a recording rule. | ||
|
@@ -612,6 +613,7 @@ type RecordingRule struct { | |
LastError string `json:"lastError,omitempty"` | ||
EvaluationTime float64 `json:"evaluationTime"` | ||
LastEvaluation time.Time `json:"lastEvaluation"` | ||
Type string `json:"type"` | ||
} | ||
|
||
// Alert models an active alert. | ||
|
@@ -721,11 +723,13 @@ func (rg *RuleGroup) UnmarshalJSON(b []byte) error { | |
|
||
for _, rule := range v.Rules { | ||
alertingRule := AlertingRule{} | ||
alertingRule.Type = string(RuleTypeAlerting) | ||
if err := json.Unmarshal(rule, &alertingRule); err == nil { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. So first of all this code was wrong, we don't even capture error anywhere no? How you got that There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think we are not justing the UnmarshalJSON function at all now that I see, we should be using UnMarshalJSON instead of json.UnMarshal what do you think? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I think changing the commentary on the Rules might be a better way since then we have a clear way of checking how the type field exists which is not clear right now. But you know the code better than me so happy to comply with what you think :) There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. again, let's add unit test for your "broken" case and we will go from there (: |
||
rg.Rules = append(rg.Rules, alertingRule) | ||
continue | ||
} | ||
recordingRule := RecordingRule{} | ||
recordingRule.Type = string(RuleTypeRecording) | ||
if err := json.Unmarshal(rule, &recordingRule); err == nil { | ||
rg.Rules = append(rg.Rules, recordingRule) | ||
continue | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If we look on
Rules
type commentary you see the canonical way to identify if it's recording or alerting is through a type system. This means we don't need this type field here.From the error you are getting, it sounds like you have problem with something marshalling this type back to JSON and then something unmarshalling (decoding) and expecting
type
field? In this case:Type
in this code -- unless I am wrong, but reproduction test will verify (:MarshalJSON
function that adds that field just for marshalling, WDYT? Alternatively we could keep this PR, but perhaps change the commentary onRules
slice? Otherwise we will have multiple ways of doing same thing.To sum up, regression test that breaks on old code would be amazing, in minimum, WDYT?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So in our use case we simply call the Rules endpoint using the prometheus API here https://github.com/prometheus/client_golang/blob/main/api/prometheus/v1/api.go#L1202. In doing so it calls the ruler endpoint and returns us a RulesResult struct which we just use as a data field in response json. But it seems like when internally in api.go we are trying to create unmarshall RuleResult struct and while doing so unmarshall alertingRule and recordingRule it expects the struct to have the type field to unmarshal the json successfully which it gets from the ruler endpoint.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Cool. So literally Prometheus server is targeted, right? Then Prometheus server should give us
type
field and our code should work without this PR. In factalertingRule.Type = string(RuleTypeAlerting)
line does nothing given you addedtype
field, but even without type field unmarshal should work because of anonymous struct with type we unmarshal first.BUT, if you notice a problem there might be one, so the best is to create a very small unit test that e.g. mock Prometheus API returning recording and alerting with type specified. Then without your change it should fail, right?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We don't have enough tests so it would be amazing anyway 🤗 - if not done I can try do it, but it will take time (busy).