Skip to content

Commit 90d45e7

Browse files
authored
Ensure Alerting Rules Not Generated for Empty Alerting Fields on TF State File (#939)
Updates Terraform Provider to ensure Alerting rules are not generated for instances where the Alerting field on the Terraform state file is not specified by the user
1 parent 7124d3e commit 90d45e7

File tree

2 files changed

+92
-12
lines changed

2 files changed

+92
-12
lines changed

internal/resources/slo/resource_slo.go

Lines changed: 14 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -298,22 +298,29 @@ func packSloResource(d *schema.ResourceData) (gapi.Slo, error) {
298298
tflabels = packLabels(labels)
299299
}
300300

301-
alerting := d.Get("alerting").([]interface{})
302-
if len(alerting) > 0 {
303-
alert := alerting[0].(map[string]interface{})
304-
tfalerting = packAlerting(alert)
305-
}
306-
307301
slo := gapi.Slo{
308302
UUID: d.Id(),
309303
Name: tfname,
310304
Description: tfdescription,
311305
Objectives: tfobjective,
312306
Query: tfquery,
313-
Alerting: &tfalerting,
307+
Alerting: nil,
314308
Labels: tflabels,
315309
}
316310

311+
if alerting, ok := d.GetOk("alerting"); ok {
312+
alertData := alerting.([]interface{})
313+
314+
// if the Alerting field is an empty block, alertData[0] has a value of nil
315+
if alertData[0] != nil {
316+
// only pack the Alerting TF fields if the user populates the Alerting field with blocks
317+
alert := alertData[0].(map[string]interface{})
318+
tfalerting = packAlerting(alert)
319+
}
320+
321+
slo.Alerting = &tfalerting
322+
}
323+
317324
return slo, nil
318325
}
319326

internal/resources/slo/resource_slo_test.go

Lines changed: 78 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -18,9 +18,11 @@ func TestAccResourceSlo(t *testing.T) {
1818
var slo gapi.Slo
1919
resource.ParallelTest(t, resource.TestCase{
2020
ProviderFactories: testutils.ProviderFactories,
21-
CheckDestroy: testAccSloCheckDestroy(&slo),
21+
// Implicitly tests destroy
22+
CheckDestroy: testAccSloCheckDestroy(&slo),
2223
Steps: []resource.TestStep{
2324
{
25+
// Tests Create
2426
Config: testutils.TestAccExample(t, "resources/grafana_slo/resource.tf"),
2527
Check: resource.ComposeTestCheckFunc(
2628
testAccSloCheckExists("grafana_slo.test", &slo),
@@ -34,6 +36,7 @@ func TestAccResourceSlo(t *testing.T) {
3436
),
3537
},
3638
{
39+
// Tests Update
3740
Config: testutils.TestAccExample(t, "resources/grafana_slo/resource_update.tf"),
3841
Check: resource.ComposeTestCheckFunc(
3942
testAccSloCheckExists("grafana_slo.update", &slo),
@@ -46,6 +49,26 @@ func TestAccResourceSlo(t *testing.T) {
4649
resource.TestCheckResourceAttr("grafana_slo.update", "objectives.0.window", "7d"),
4750
),
4851
},
52+
{
53+
// Tests that No Alerting Rules are Generated when No Alerting Field is defined on the Terraform State File
54+
Config: noAlert,
55+
Check: resource.ComposeTestCheckFunc(
56+
testAccSloCheckExists("grafana_slo.no_alert", &slo),
57+
testAlertingExists(false, "grafana_slo.no_alert", &slo),
58+
resource.TestCheckResourceAttrSet("grafana_slo.no_alert", "id"),
59+
resource.TestCheckResourceAttr("grafana_slo.no_alert", "name", "No Alerting Check - does not generate Alerts"),
60+
),
61+
},
62+
{
63+
// Tests that Alerting Rules are Generated when an Empty Alerting Field is defined on the Terraform State File
64+
Config: emptyAlert,
65+
Check: resource.ComposeTestCheckFunc(
66+
testAccSloCheckExists("grafana_slo.empty_alert", &slo),
67+
testAlertingExists(true, "grafana_slo.empty_alert", &slo),
68+
resource.TestCheckResourceAttrSet("grafana_slo.empty_alert", "id"),
69+
resource.TestCheckResourceAttr("grafana_slo.empty_alert", "name", "Empty Alerting Check - generates Alerts"),
70+
),
71+
},
4972
},
5073
})
5174
}
@@ -74,15 +97,30 @@ func testAccSloCheckExists(rn string, slo *gapi.Slo) resource.TestCheckFunc {
7497
}
7598
}
7699

77-
func testAccSloCheckDestroy(slo *gapi.Slo) resource.TestCheckFunc {
100+
func testAlertingExists(expectation bool, rn string, slo *gapi.Slo) resource.TestCheckFunc {
78101
return func(s *terraform.State) error {
102+
rs := s.RootModule().Resources[rn]
79103
client := testutils.Provider.Meta().(*common.Client).GrafanaAPI
80-
err := client.DeleteSlo(slo.UUID)
104+
gotSlo, _ := client.GetSlo(rs.Primary.ID)
105+
*slo = gotSlo
106+
107+
if slo.Alerting == nil && expectation == false {
108+
return nil
109+
}
81110

82-
if err == nil {
83-
return fmt.Errorf("SLO with a UUID %s still exists after destroy", slo.UUID)
111+
if slo.Alerting != nil && expectation == true {
112+
return nil
84113
}
85114

115+
return fmt.Errorf("SLO Alerting expectation mismatch")
116+
}
117+
}
118+
119+
func testAccSloCheckDestroy(slo *gapi.Slo) resource.TestCheckFunc {
120+
return func(s *terraform.State) error {
121+
client := testutils.Provider.Meta().(*common.Client).GrafanaAPI
122+
client.DeleteSlo(slo.UUID)
123+
86124
return nil
87125
}
88126
}
@@ -104,6 +142,41 @@ resource "grafana_slo" "invalid" {
104142
}
105143
`
106144

145+
const emptyAlert = `
146+
resource "grafana_slo" "empty_alert" {
147+
description = "Empty Alerting Check - generates Alerts"
148+
name = "Empty Alerting Check - generates Alerts"
149+
objectives {
150+
value = 0.995
151+
window = "28d"
152+
}
153+
query {
154+
type = "freeform"
155+
freeform {
156+
query = "sum(rate(apiserver_request_total{code!=\"500\"}[$__rate_interval])) / sum(rate(apiserver_request_total[$__rate_interval]))"
157+
}
158+
}
159+
alerting {}
160+
}
161+
`
162+
163+
const noAlert = `
164+
resource "grafana_slo" "no_alert" {
165+
description = "No Alerting Check - does not generate Alerts"
166+
name = "No Alerting Check - does not generate Alerts"
167+
objectives {
168+
value = 0.995
169+
window = "28d"
170+
}
171+
query {
172+
type = "freeform"
173+
freeform {
174+
query = "sum(rate(apiserver_request_total{code!=\"500\"}[$__rate_interval])) / sum(rate(apiserver_request_total[$__rate_interval]))"
175+
}
176+
}
177+
}
178+
`
179+
107180
func TestAccResourceInvalidSlo(t *testing.T) {
108181
testutils.CheckCloudInstanceTestsEnabled(t)
109182

0 commit comments

Comments
 (0)